Headery a struktury – C / C++ – Fórum – Programujte.com
 x   TIP: Přetáhni ikonu na hlavní panel pro připnutí webu

Headery a struktury – C / C++ – Fórum – Programujte.comHeadery a struktury – C / C++ – Fórum – Programujte.com

 

Toto vlákno bylo označeno za vyřešené.
Scrat0
Návštěvník
23. 11. 2014   #1
-
0
-

1) Nejak porad nechapu jak fungujou headery, konkretne mam v jednom headeru (header1) napsanou definici struktury (struct1), v headeru mainu mam dalsi definici struktury (struct2) ve ktere je jako clen pouzita struktura struct1. Jenze to nefunguje ikdyz je pripojen header1, funguje to jen kdyz tu strukturu v niz je jina struktura hodim do .cpp a v headeru necham jen deklaraci struct2 a predbezne deklarovanou struct1.

Takze ma pro header to, ze je v nem  pres #include pripojenej jinej header vubec nejakej vliv, nebo se to projevi az v cpp.

2) Jo mozne napsat strukturu tak, aby clenem byla trida bez specifikovaneho konstruktoru. Me to porad hazi chybu dokud tam nedam napevno jeden z konstruktoru.

Doufam ze to oboji staci obecne, kdyztak poslu i kod.

Nahlásit jako SPAM
IP: 88.100.129.–
ingiraxo+15
Grafoman
23. 11. 2014   #2
-
0
-

#1 Scrat
struktůry by správně měli být pouze v hlavičce nebo tam, kde jsou potřeba.. rozhodně bych z nich nedělal deklaraci a definici jinde - to je naprosto k ničemu

hlavně když to takto uděláš, tak je potřeba definovat i bezparametrický konstruktor

spíše uveď příklad, jestli si skutečně rozumíme

Nahlásit jako SPAM
IP: 213.168.183.–
Moje aplikace: http://ophite.cz
Tutoriály na: C#
KIIV
~ Moderátor
+43
God of flame
23. 11. 2014   #3
-
0
-

Jinak include znamena jen to, ze se na to misto hodi obsah toho souboru.

Nahlásit jako SPAM
IP: 94.113.95.–
Program vždy dělá to co naprogramujete, ne to co chcete...
24. 11. 2014   #4
-
+1
-
Zajímavé

Hlavičkové soubory lze vkládat do sebe: hlavičkový soubor (např hl1.h) se struct1 vložíš do hlavičkového souboru (např hl2.h) se struct2. Hl2.h pak vložíš do .c souboru s funkcí main. Důležité je zabránit cyklickému a opakovanému vkládání hlavičkových souborů.

hu

Nahlásit jako SPAM
IP: 2001:67c:1222:800:8fa:4c7...–
Scrat0
Návštěvník
24. 11. 2014   #5
-
0
-

Tak priklad toho co bych chtel, ale nejde me to :(

header rect.h

#pragma once

struct rectInt
{
  int left;
  int top;
  int right;
  int bottom;
};

header mainu

#pragma once

#include "C:\Temp\rect.h"

struct test 
{
  struct rectInt a; 
  struct rectInt b;  
};

Chyby: error C2079: 'test::a' uses undefined struct 'rectInt'

Pokud struct test hodim do cpp, tak se to zkompiluje.

Nahlásit jako SPAM
IP: 88.100.129.–
Scrat0
Návštěvník
24. 11. 2014   #6
-
0
-

A jeste otazka mimo, jak probiha vypocet pri pouziti ruznych typu.

Jako treba: long = int * float + double

Jestli se pouziva pro vypocet jeden z uvedenych typu podle nejakeho klice, jako treba prvni pouzity, nebo ten nejpresnejsi... Jde me o to jestli se vysledek pocita presne a zaokrouhli se az nakonec do longu, nebo se treba protoze je prvni int pocita porad jen v celych cislech.


Nahlásit jako SPAM
IP: 88.100.129.–
KIIV
~ Moderátor
+43
God of flame
24. 11. 2014   #7
-
0
-

#6 Scrat
jede se postupne.. nejspis se vypocita nasobeni jako float, pricte se a zvetsi se to na double..

nejnebezpecnejsi je to u deleni   1/2  se bere jako  int/int  a vysledek je pak 0 (celociselne deleni 0 + zbytek 1)

Nahlásit jako SPAM
IP: 94.113.95.–
Program vždy dělá to co naprogramujete, ne to co chcete...
24. 11. 2014   #8
-
0
-

na kolika místech se vyskytuje #include "C:\Temp\rect.h"? Myslím, že ho máš v main.c kde nemá být

hu

Nahlásit jako SPAM
IP: 193.86.81.–
ingiraxo+15
Grafoman
24. 11. 2014   #9
-
0
-

#5 Scrat
to co si napsal je validní, ale nelíbí se mi tam ten include, proč tam nedáš jen

#include "rect.h"

hádám, že header máš přímo v projektu.. nejsem si jistej, jestli tam vůbec může být takto absolutní cesta, což je i blbost když se nad tím zamyslíš :)

Nahlásit jako SPAM
IP: 213.168.183.–
Moje aplikace: http://ophite.cz
Tutoriály na: C#
24. 11. 2014   #10
-
0
-

Může tam být absolutní nebo relativní cesta. Další možnost je mít to nastavený v include path, třetí možnost je vložit do projektu.

hu

Nahlásit jako SPAM
IP: 193.86.81.–
Scrat0
Návštěvník
25. 11. 2014   #11
-
0
-

#8 hlucheucho
Jestli je tim main.c mysleno to cemu rikam main.cpp, tak tam neni. Respektive ve vsech cpp mam Includnutej jen header kterej k nemu patri.

Jinak kdyz najedu ve struct test na struct rectInt a dam najet na definici nebo deklaraci tak skoci do spravneho headeru (kde je struktura definovana), ikdyz je v headeru mainu, kde pri kompilaci hodi ze struktura rectInt neni definovana.

Jeste me napada jestli to nemuze souviset s nastavenim cpp, kde mam asi u vsech aktivni volbu "Precompiled header" -> Not Using Precompiled Headers

Nahlásit jako SPAM
IP: 88.100.129.–
25. 11. 2014   #12
-
0
-

 Zkus

//vytvoříš nový datový typ
typedef struct
{
  int left;
  int top;
  int right;
  int bottom;
} rectInt;

použití je jako běžná proměnná: 

//nový datový typ použiješ ve struktuře
typedef struct 
{
  rectInt a; 
  rectInt b;  
} test;

Vždy používám typedef a nikdy jsem neměl problém.

hu

Nahlásit jako SPAM
IP: 2001:67c:1222:800:288f:22...–
Scrat0
Návštěvník
25. 11. 2014   #13
-
0
-

#12 hlucheucho
V teto typedef verzi to hlasi chybu (jmeno promenne "a" je podtrzeno) hned po zapsani, po najezdu to pise "incomplete type is not allowed". A po najezdu na rectInt a odkliknuti "go to definition" ho to nenajde. 

Nahlásit jako SPAM
IP: 88.100.129.–
25. 11. 2014   #14
-
0
-

co máš za překladač? Nemáš v názvech souborů a adresářů (českou) diakritiku? Některé překladače (např. Atmel Studio) s tím mají problém

hu

Nahlásit jako SPAM
IP: 193.86.81.–
Scrat0
Návštěvník
25. 11. 2014   #15
-
0
-

#14 hlucheucho
Microsoft Visual C++ 2010 Express

Nahlásit jako SPAM
IP: 88.100.129.–
25. 11. 2014   #16
-
0
-

a ty adresáře?

hu

Nahlásit jako SPAM
IP: 193.86.81.–
Scrat0
Návštěvník
25. 11. 2014   #17
-
0
-

#16 hlucheucho
Otestoval jsem to presne s tim C:\Temp\ a stejny. Jeste muzu zkusit dat to tedy nekam kde to najde sam bez psani cesty.

Nahlásit jako SPAM
IP: 88.100.129.–
25. 11. 2014   #18
-
0
-

MS VS má vnořené hlavičkové soubory např v stdafx.h. Pokud struktura adresářů a názvů souborů neobsahuje diakritiku není problém, ty konstrukce, co jsem ti s typedef dal, se bez potíží přeloží.

hu

Nahlásit jako SPAM
IP: 193.86.81.–
Scrat0
Návštěvník
25. 11. 2014   #19
-
0
-

#18 hlucheucho
Hm, vypada to, ze to fakt bude tou diakritikou, aspon testovne vytvorenej projekt s tema strukturama funguje.

Stavajici projekt je v adresarove strukture s diakritikou.

Projekt se asi neda preulozit co? Nebo jak ho jednoduse presunout... 

Nahlásit jako SPAM
IP: 88.100.129.–
Scrat0
Návštěvník
25. 11. 2014   #20
-
0
-

Divny, projekt i vsechny soubory a cesty jsem bez diakritiky a problem je zpet. 

Nahlásit jako SPAM
IP: 88.100.129.–
26. 11. 2014   #21
-
0
-

asi budeš muset postnout celý kód, nebo celý projekt dej v zipu na nějakou úschovnu jako letecká pošta apod. Jinak se nedobereme příčiny.

hu

Nahlásit jako SPAM
IP: 2001:67c:1222:800:c45d:48...–
Scrat0
Návštěvník
26. 11. 2014   #22
-
0
-

#21 hlucheucho
Jeste jeden pokus... nasel jsem radek, kterej rozhoduje o tom, jestli se to zkompiluje nebo ne. 

struct.h

#pragma once

#include "c:\Programovani\test\test\test.h"

struct rectInt
{
  int left;
  int top;
  int right;
  int bottom;

    public:
	  void inline Set(int x, int y, int x2, int y2){left=x; top=y; right=x2; bottom=y2; return;};
};

struct.cpp - pokud vykomentuju tento include (a nasledne i pouziti struktury ve funkci), tak se to zkompiluje

#pragma once

#include "C:\Programovani\test\bitmap\struct.h" //zdroj chyby

void fce()
 {
   rectInt bb;
   bb.right=10;
   return;
 };

test.h 

#pragma once

#include "C:\Programovani\test\bitmap\struct.h"
#include <windows.h> 
#include <tchar.h> 

struct bod2D_16
{
 INT16 X;
 INT16 Y;
 public:
   void Set(INT16 X, INT16 Y){bod2D_16::X=X; bod2D_16::Y=Y; return;};
};

struct test
{
  struct rectInt a;
};

test.cpp - funkcni jen pokud je vykomentovany include v struct.cpp, jinak chyba - pouzita nedefinovana struktura

#pragma once

#include "test.h"

int _tmain(int argc, _TCHAR* argv[])
{
  test ooo;
  ooo.a.left=10;
	
  return 0;
};
Nahlásit jako SPAM
IP: 88.100.129.–
26. 11. 2014   #23
-
0
-

do struct.h vkládáš test.h a do test.h vkládáš struct.h. To je cyklické vkládání a vzniká zmatek. Tím, že je použita pragma se zabrání opakovanému vložení a tak se to někam vloží, otázka kam. Že se to nevloží opakovaně současně způsobí, že to někde chybí. Prostě se takovým konstrukcím vyhni. Vkládané soubory mohou tvořit strom, různě rozvětvený - s tím není problém, ale nesmí tvořit kruh - do toho se snadno zamotáš.

hu

Nahlásit jako SPAM
IP: 2001:67c:1222:800:c45d:48...–
26. 11. 2014   #24
-
0
-

 hlavičkový soubor by měl obsahovat datové typy (třeba struktury) a deklarace funkcí. cpp by pak měl obsahovat implementaci funkcí. Pokud "struktura" obsahuje funkci, asi by bylo vhodnější to mít jako class, tam hlavičkový soubor obsahuje deklarace atributů (proměnné) a metod (funkce), cpp pak implementaci metod. U class je pak potřeba se zamyslet i nad tím, jak se s takovým objektem bude pracovat - vznik objektu, kopírování a zánik objektu. Ne vždy vyhovují defaultní konstruktory a destruktor.

hu

Nahlásit jako SPAM
IP: 2001:67c:1222:800:c45d:48...–
Scrat0
Návštěvník
26. 11. 2014   #25
-
0
-

#24 hlucheucho
Diky za pomoc. Vedel jsem ze je to cyklicke, ale veril jsem ze toto resi pragma :(

Do tech struktur davam max. funkci na jejich snadne plneni, protoze jinak to musim rozepisovat po clenech. Respektive 

test x = {10,10,10}; //pri inicializaci jde vsechny cleny zapsat                        //najednou
x = {20,20,20}; //tohle uz nefunguje a nevim jak jinak to udelat                   //nez pres tu funci

Nahlásit jako SPAM
IP: 88.100.129.–
26. 11. 2014   #26
-
0
-

u třídy (class) jde udělat parametrický konstruktor, kterému počáteční hodnoty předáš jako parametry 

MyClass *cl;

cl = new MyClass(30, 20, 10);

ukázka případu, kdy defaultní konstruktor nevyhovuje a proto je lepší si vytvořit svůj, parametrický.

hu

Nahlásit jako SPAM
IP: 193.86.81.–
Scrat0
Návštěvník
27. 11. 2014   #27
-
0
-

Ted me vrta hlavnou tohle...

long pomIdx[100];

//tohle funguje
long * arPt = pomIdx;
funkce (&arPt); //fce chce parametr long **

//a tohle ne
funkce (&pomIdx);

Tedy nekde jsem zahlid, ze je nejakej rozdil mezi ukazatelem a polem, tak to bude asi tim, ze z pole nejde udelat ukazatel na ukazatel, zatimco z ukazatele to jde. Ale at uz je to tim nebo ne, tak kdyby to slo nejak jednoduse vysvetlit.

Nahlásit jako SPAM
IP: 88.100.129.–
27. 11. 2014   #28
-
0
-

V prvním případě arPt je ukazatel, v podstatě "proměnná jako každá jiná". Takže pro něj platí to, co pro běžnou proměnnou, lze získat adresu kde se nachází pomocí &.  U druhého příkladu bych zkusil 

funkce (&pomIdx[]);

hu

Nahlásit jako SPAM
IP: 2001:67c:1222:800:941e:ff...–
Scrat0
Návštěvník
27. 11. 2014   #29
-
0
-

To neskousne

funkce (&pomIdx[]); //chyba: expected an expression
Nahlásit jako SPAM
IP: 88.100.129.–
ingiraxo+15
Grafoman
27. 11. 2014   #30
-
0
-

#29 Scrat
já teda přesně nevim o co se snažíš, ale pokud chceš dostal to pole do fce, tak normálně 

void update(long* arr, int size)
{
    *arr = 100; // nastavi prvni prvek na 100
}

int main()
{
    long pomIdx[100] = { 0 };

    update(pomIdx, sizeof(pomIdx) / sizeof(long));

    cout << *pomIdx; // vypise 1.prvek - hodnotu 100

    return EXIT_SUCCESS;
}
Nahlásit jako SPAM
IP: 213.168.183.–
Moje aplikace: http://ophite.cz
Tutoriály na: C#
KIIV
~ Moderátor
+43
God of flame
27. 11. 2014   #31
-
0
-

#29 Scrat
cela pointa  long ** neco  je v tom, ze se muze zmenit pointer na adrese v neco.. no a u statickyho pole by to byl dost problem. Proto funguje udelat si pointer a predat adresu na ten, a je to problem zvladnout bez toho mezikroku.

Nahlásit jako SPAM
IP: 94.113.95.–
Program vždy dělá to co naprogramujete, ne to co chcete...
Scrat0
Návštěvník
28. 11. 2014   #32
-
0
-

#30 ingiraxo
Chci ten ukazatel na pole zmenit. Funkce nastavuje nove pole o nejake velikosti, vyplni ho a vrati.

Nahlásit jako SPAM
IP: 88.100.129.–
ingiraxo+15
Grafoman
28. 11. 2014   #33
-
0
-

#32 Scrat
aha, tak v tom případě 

// IN/OUT pole, OUT nova velikost
void update(long* arr, int& len)
{
    long newArr[] = { 1, 2, 3, 4, 5 }; // novy pole
    len = sizeof(newArr) / sizeof(*newArr);
    memmove(arr, newArr, sizeof(newArr));
}

v main() použiješ potom normálně 

int main()
{
    long arr[100] = { 0 };

    int len; // v tomhle pripade se nastavi fci 'update' hodnota 5
    update(arr, len); // nahradi za {1,2,3,4,5}

    return EXIT_SUCCESS;
}

PS: se statickým polem se s v tomhle případě špatně pracuje, tady bych spíš použil alokovaný pole (ideálně kolekci)... nebo fci vracet nový pole návratovou hodnotou a né přes parametr

Nahlásit jako SPAM
IP: 213.168.183.–
Moje aplikace: http://ophite.cz
Tutoriály na: C#
Scrat0
Návštěvník
28. 11. 2014   #34
-
0
-

#33 ingiraxo
Asi taky moznost, ten vypocet "len" me prijde moc slozitej. Akorat to skape pokud arr == NULL.

Nahlásit jako SPAM
IP: 88.100.129.–
ingiraxo+15
Grafoman
28. 11. 2014   #35
-
0
-

#34 Scrat
teoreticky null být nemůže, protože statický pole nejde nastavit na null - není to přímo ptr, ale špíše reference, ale klidně si tam dej kontrolu na null ;)

výpočet velikosti tam být musí, protože nová velikost nemusí být stejná (jednoduše vypočteš velikost celého pole v bytech a potom vydělíš bytovou velikosti typu prvku)

pokud by to bylo návratovou hodnotou, tak vracet novou velikost musíš stejně, jen si ušetříš jeden řádek kódu - vlastně ne, nahradíš jeden řádek za return

Nahlásit jako SPAM
IP: 213.168.183.–
Moje aplikace: http://ophite.cz
Tutoriály na: C#
Scrat0
Návštěvník
28. 11. 2014   #36
-
0
-

#35 ingiraxo
Neni to staticke pole. Ja to mam takhle 

void redefArr(long ** arPtPt, long & size)
{
  .... //pocita se size = neco
  *arPtPt = new long [size];
  long * ar = *arPtPt; 
  ar[i]=...;
  ....
  return;
};

Prave NULL je asi necastejsi parametr, takze to s nim musi fungovat.

Nahlásit jako SPAM
IP: 88.100.129.–
KIIV
~ Moderátor
+43
God of flame
28. 11. 2014   #37
-
0
-

#36 Scrat
a proc ses tam snazil nacpat referenci na staticky pole?

NULL se resi podminkou

uvolnujes pamet, kdyz prepisujes pointer?

Nahlásit jako SPAM
IP: 94.113.95.–
Program vždy dělá to co naprogramujete, ne to co chcete...
Scrat0
Návštěvník
28. 11. 2014   #38
-
0
-

Aha, uz to vidim moje chyba. Udelal jsem ty funkce vlastne 2, jednu pro dynamicky a jednu pro staticky pole, pricemz prvni byla ty dynamicka a tak jsem pouzil jeji kod a lehce ho upravil pro staticky... takze, na to staticky bude asi lepsi ta verze s memmove.

Nahlásit jako SPAM
IP: 88.100.129.–
ingiraxo+15
Grafoman
28. 11. 2014   #39
-
0
-

#38 Scrat
nemůžeš míchat statický a dyn, to co jsem psal se týkalo statickýho pole, protože jsem vycházel z tvého kódu viz. 

long pomIdx[100];

u něj není možný, aby do fce přišel null... pro dyn. pole je situace úplně jiná, hlavně nesmíš zapomenou uvolňovat pamět původního pole !! a pole jde předat parametrem jako ukazatel na referenci a opět se nevyhneš předání nové velikosti pole

např. 

void update(long*& arr, int& len)
{
  cout << "Zadej velikost pole: ";
  cin >> len;
  long* newArr = new long[len];
  for (int i = 0; i < len; i++) *(newArr + i) = i + 1;
  delete[] arr;
  arr = newArr;
}
Nahlásit jako SPAM
IP: 213.168.183.–
Moje aplikace: http://ophite.cz
Tutoriály na: C#
Scrat0
Návštěvník
28. 11. 2014   #40
-
0
-

#39 ingiraxo
Jsem jen nejak zapomel, ze jsem kdesi nahore poslal ten kod se statickym a presel jsem tedy na tu druhou fci. s dynamickym, Jo delete tam uz je i druhej parametr s velikosti pole.

Nahlásit jako SPAM
IP: 88.100.129.–
Scrat0
Návštěvník
28. 11. 2014   #41
-
0
-

Jeste kdyz mam tady vas chytry, nevite o nejake matematicke knihovne, ktera umi spocitat plochy jakekoliv uzavreneho polygonu, jehoz strany jsou kombinaci cehokoliv od usecek, po casti elips, parabol atd.

Nahlásit jako SPAM
IP: 88.100.129.–
ingiraxo+15
Grafoman
29. 11. 2014   #42
-
0
-

noo.. vzhledem k tomu, že tenhle topic se NEjmenuje "Pomožme Scatovi", ale "Headery a struktury" a už rozebíráme 3 téma z úplně jiného soudku, tak bych to možná utnul v zárodku a vytvořil nový topic.. co ty na to? hm?

Nahlásit jako SPAM
IP: 213.168.183.–
Moje aplikace: http://ophite.cz
Tutoriály na: C#
Scrat0
Návštěvník
29. 11. 2014   #43
-
0
-

#42 ingiraxo
Tak jo, ja jen nechtel porad zakladat nova temata kvuli kazde blbosti.

Nahlásit jako SPAM
IP: 88.100.129.–
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, 27 hostů

Podobná vlákna

Struktury — založil Samuel Lehotský

Struktury v C++ — založil pin2k

Struktury — založil Matěj Andrle

Struktury - please help — založil Krang

Struktury — založil RePRO

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ý