Funkce na sestavení cesty vrací nesprávný string – C / C++ – Fórum – Programujte.com
 x   TIP: Přetáhni ikonu na hlavní panel pro připnutí webu

Funkce na sestavení cesty vrací nesprávný string – C / C++ – Fórum – Programujte.comFunkce na sestavení cesty vrací nesprávný string – C / C++ – Fórum – Programujte.com

 

Toto vlákno bylo označeno za vyřešené.
oxidián0
Grafoman
15. 8. 2017   #1
-
0
-

header

https://paste.ofcode.org/3GmzmFCjfbg4uHtJfr7YvX

c file:

https://paste.ofcode.org/dXCRVU8jEL2yYfKPhHAYUt

Nekopíruju adresářovou strukturu db, takže jestli mi s tím chceš pomoci, na řádku 146 funkce readfile bude vždy vracet null pointer.

Nicméně já mám debugger nastavený takto:

breakpoint na řádku 118: ve funkci prepareFilePath, větev else.

breakpoint na řádku 150.

Když se to zastaví na řádku 150 hodnota filename je

db/radiation/insolation incident/\"/maximum direct radiation.txt

ale předtím ještě před vrácením filename, na řádku 118, respektive na 127 byl filename správně

db/radiation/insolation incident/July 1983 - June 2005/insolation - clear sky - horizontal surface.txt

Funkci char * prepareFilePath(TABLE_ tmain, TABLE_ tob, char filename[])

jsem původně měl deklarovanou takto:

char * prepareFilePath(TABLE_ tmain, TABLE_ tob, char * filename) ...

Jenže filename je pole char:

char * prepareBuffer(TABLES * tables, char * buf, TABLE_ * table_arrays[]){
    char filename[400];

takže jsem to opravil

char * prepareFilePath(TABLE_ tmain, TABLE_ tob, char filename[])


Nicméně to nemá vliv, program se chová stále stejně. Několik cest mi prošlo bez problému, a tady u této to dělá problém.cesta se skládá ze řádku

5 (hlavní adresář), 14 (podadresář), 6 (druhý soubor)

Nahlásit jako SPAM
IP: 78.102.61.–
oxidián0
Grafoman
15. 8. 2017   #2
-
0
-

Kód té funkce po odstranění komentářů.

char * prepareFilePath(TABLE_ tmain, TABLE_ tob, char filename[])
{
    if ( strlen (tob.submain_directory))
        sprintf(filename, "db/%s/%s/%s", tmain.main_directory,tob.submain_directory,tob.filename );
    else
        sprintf(filename, "db/%s/%s/%s", tmain.main_directory,tmain.submain_directory,tob.filename );
  return filename; // zde je hodnota filename správně
}

Už jsem na to přišel. Tak problém byl někde jinde.

tob.submain_directory není vynulovaný a je v něm hodnota \"\000

V důsledku toho mi nevýjde test strlen (tob.submain_directory)
.

Nahlásit jako SPAM
IP: 78.102.61.–
15. 8. 2017   #3
-
0
-

Přehršel ukazatelů ve funkci
char * readfile(char * name, int skip, char * buf, int bufLen, int shift )

"Nehrabe" se některý z nich, kde nemá? Úvaha: po návratu z funkce prepareFilePath se volá readfile.

Doporučuji break na ř. 146, podívat se na hodnotu filename (asi bude správně) a pak krok dovnitř funkce readfile, krokovat tuto funkci a sledovat, co se děje.

hu

Nahlásit jako SPAM
IP: 195.178.67.–
KIIV
~ Moderátor
+43
God of flame
15. 8. 2017   #4
-
0
-

Takze dalsi lekce: lokalni promenne se samy nenuluji :D

Nahlásit jako SPAM
IP: 93.91.151.–
Program vždy dělá to co naprogramujete, ne to co chcete...
oxidián0
Grafoman
15. 8. 2017   #5
-
0
-

Ono by to chtělo vynulovat celý ten struct

TABLES tables;

mohu na to použít

void * memset ( void * ptr, int value, size_t num );

memset ( &tables, 0, sizeof(tables) ); ???

Nahlásit jako SPAM
IP: 78.102.61.–
15. 8. 2017   #6
-
0
-

Takze dalsi lekce: lokalni promenne se samy nenuluji 

a opět ze základních věcí.

Pár drobností:
1. Jednou používáš jako parametr char neco[] (ve funkci prepareFilePath), jinde char* cosi. Je to formalita, ale sjednotil bych to.
2. Pokud funkce vrací char*, pak se mi jeví vhodnější return NULL (ve funkci readfile). Dále by měla být návratová hodnota vracena v každé větvi funkce (např. funkce prepareBuffer nevrací nic a při tom má vracet char*)

Nejjednodušší metoda, jak "vynulovat" řetězec: 

char text[10];

text[0] = '\0';

Výsledkem je prázdný řetězec.

hu

Nahlásit jako SPAM
IP: 195.178.67.–
KIIV
~ Moderátor
+43
God of flame
15. 8. 2017   #7
-
0
-

#5 oxidián
V C to pujde.

Nahlásit jako SPAM
IP: 93.91.151.–
Program vždy dělá to co naprogramujete, ne to co chcete...
oxidián0
Grafoman
15. 8. 2017   #8
-
0
-

vracet [] přece nejde, tak jsem tam nechal pointer; nevěděl jsem co s tím

Tak jo, to vynulování funguje, takže jsem úspěšně odbugoval první fázi programu.

Nahlásit jako SPAM
IP: 78.102.61.–
15. 8. 2017   #9
-
0
-

Ono by to chtělo vynulovat celý ten struct

Na tom se dobře demonstruje výhoda objektového programování. Představ si TABLES jako objekt, kde v jeho konstruktoru nastavíš defaultní stav. Pak při tvorbě instancí objektu voláš konstruktor a tím dostaneš instanci v defaultním stavu i v případě, že instanci vytváříš lokálně. Konstruktor napíšeš jen jednou a pak už na to nemusíš myslet.

hu

Nahlásit jako SPAM
IP: 195.178.67.–
JerryM0
Věrný člen
15. 8. 2017   #10
-
0
-

#8 oxidián
to s tim vracením pole že jako nejde neni až tak uplně pravda třeba tohle de:  :)

typedef struct ts_THelper {
     int array[3];
} ts_Helper;

ts_THelper fnc() {
 
    ts_THelper array;
    return array;
}

Nahlásit jako SPAM
IP: 2a00:1028:83be:235a:89d6:...–
MilanL+1
Grafoman
16. 8. 2017   #11
-
0
-

#1 oxidián
Ahoj, koukal jsem na ty kody, ten readfile ještě asi nemáš dodělaný, taková drobnost, pokud to budeš do paměti natahovat jako 24bit nemusíš s těmi čísly nijak extra manipulovat stačí jít číslo po čísle a uložit 3 x 8b:

for (i=0;i<12;i++){
s -=3;
s[0] = m[i];
s[1] = m[i] >> 8;
s[2] = m[i] >> 16;}

jinak pokud s tím chceš pracovat, možná by nebylo naškodu si na to nadefinovat datový typ, kde bys měl i ty své konverze float > uint24 > float - měl bys pak další práci s tím o hodně jednodušší.

Nahlásit jako SPAM
IP: 91.139.9.–
MilanL+1
Grafoman
17. 8. 2017   #12
-
0
-

#11 MilanL

jen jsem si ted když jsem na to koukal po druhé všiml že do MSB dáváš jen 2 bity tzn pracuješ s 18 a ne 24b
* k tomu readfile co tam máš, neviděl jsem tam 1 věc a sice uložení  MSB (s vyššími 2 bity všech hodnot celkem 24b) do bufferu.

Nahlásit jako SPAM
IP: 91.139.9.–
oxidián0
Grafoman
18. 8. 2017   #13
-
0
-

Budu to řešit později. Teď jsem si dal od toho pauzu a budu se muset nad tím opět zamyslet.

Pokud si pamatuju z paměti:

MSB má fungovat takto: 12x cyklus ve kterém provádím 2x kopírování a posun. Celkem se uloží 2x12 bitů výsledkem má být 24 bitů čili 3 byty.

LSB má mít zbývajících 12x16 bytů.

Jinými slovy jsem rozdělil 18 bytů x 12 na (2+16) * 12.

Nahlásit jako SPAM
IP: 78.102.61.–
Zjistit počet nových příspěvků

Přidej příspěvek

Toto téma je starší jak čtvrt roku – přidej svůj příspěvek jen tehdy, máš-li k tématu opravdu co říct!

Ano, opravdu chci reagovat → zobrazí formulář pro přidání příspěvku

×Vložení zdrojáku

×Vložení obrázku

Vložit URL obrázku Vybrat obrázek na disku
Vlož URL adresu obrázku:
Klikni a vyber obrázek z počítače:

×Vložení videa

Aktuálně jsou podporována videa ze serverů YouTube, Vimeo a Dailymotion.
×
 
Podporujeme Gravatara.
Zadej URL adresu Avatara (40 x 40 px) nebo emailovou adresu pro použití Gravatara.
Email nikam neukládáme, po získání Gravatara je zahozen.
-
Pravidla pro psaní příspěvků, používej diakritiku. ENTER pro nový odstavec, SHIFT + ENTER pro nový řádek.
Sledovat nové příspěvky (pouze pro přihlášené)
Sleduj vlákno a v případě přidání nového příspěvku o tom budeš vědět mezi prvními.
Reaguješ na příspěvek:

Uživatelé prohlížející si toto vlákno

Uživatelé on-line: 0 registrovaných, 79 hostů

Moderátoři diskuze

 

Hostujeme u Českého hostingu       ISSN 1801-1586       ⇡ Nahoru Webtea.cz logo © 20032024 Programujte.com
Zasadilo a pěstuje Webtea.cz, šéfredaktor Lukáš Churý