Variable soll nicht gelöscht werden beim zyklischen aufrufen

OP #7574928
Lesenswert?

ich habe ein main Funktion die zyklisch aufgerufen wird, diese ruft zyklisch modul1 auf und dort modul2 welches mir einen wert berechnet. Dieser wert soll in Modul1 zur verfügung stehen und bei jedem Aufruf von modul2 kommt x dazu. Das heißt der Wert davor darf nicht gelöscht werden.

wie mache ich nun das Ganze? Lege ich eine Globale Variable in der header von modul2 an? Oder mache ich das mit static in modul1?

1
int main(void)
2
{
3
   // modul2Parameter g_mod2Par; hier global anlegen oder in modul 1?
4

5

6
modul1();
7
}
8

9

10

11
modul1()
12
{
13
  //hier als static anlegen?? static modul2Parameter mod2par;
14
  ergebis =  modul2(); // ergebnis soll in modul1 und modul zwei nicht immer bei 0 anfangen sondern den wert +x bekommen, bis die variable auf 0 in modul 2 gesetzt wird.
15
}
16

17

18

19
//modul 2 .h-Datei
20
{
21
    typedef struct
22
    {
23
        bool gestartet;
24
        int zeit;
25
    }modul2Parameter;
26

27
    extern modul2Parameter; // ODER So machen und in main von diesem Typ eine Variable anlegen?
28
}
OP #7574964
Lesenswert?

Das Ergebnis wird aber auch in einer Struktur von modul1 gespeichert. Hier habe ich einfach in "Ergebnis" zur Vereinfachung geschrieben.

Modul1 sieht so aus:

1
modul1.h
2
typedef struct
3
{
4
 int Ergebnis;
5
}mod1Parameter;

in der Main habe ich mit mod1Parameter g_module1; eine globale Variable angelegt.

#7575149
Lesenswert?

Du solltest globale Variablen möglichst vermeiden. Je größer Projekte werden, desto höher das Risiko dass es dadurch zu Problemen kommt (mehrere Module verändern ungewollt den Inhalt...).

Deine Beschreibung ist etwas wirr.

Wenn ich recht verstehe liefert Modul2 einen (Zeit?)Wert den du an Modul1 übergibst? Oder willst Du eine ganze Struktur (modul2Parameter) zurückgeben? Modul1 soll den Wert auf eine Summenvariable aufaddieren, es sei denn es kommt ein Wert 0 vom Modul2 zurück. Ist der Zahlenwert aus Modul2 eine Zeitdifferenz oder eine absolute Zeit?

Egal was die Aufgabe des Programmes ist: Versuche dir eine "verständliche" Schnittstelle ohne globale Variablen zu definieren. Codezeile wie "ergebis = modul2();" ist unverständlich. Versuche beschreibende Namen zu nutzen.

Persönliche Seite #7575154
Lesenswert?

Wie ist das zu verstehen dass die main zyklisch aufgerufen wird? Typischer Weise wird ein Programm beendet, wenn die main verlassen wird. Dabei wäre es guter Stil, einen sinnvollen Return Wert an das Betriebssystem zurückzugeben.

Wenn du die Unterfunktion zyklisch aufrufen willst, kannst du eine Schleife in der Main einbauen. Dann könntest du deine Daten als lokale variable in der Main verwalten.

Gast #7575207
Lesenswert?

Was genau ist hier ein "Modul"?

Mir scheint, dass eine Funktion gemeint ist. Aber warum nennst du sie dann "Modul"?

Wie gesagt kannst du innerhalb einer Funktion eine Variable als static kennzeichnen, damit sie ihren Wert bei Verlassen der Funktion nicht vergisst.

Möchtest du, dass eine Gruppe von Funktionen Zugriff auf dazu gehörige Daten hat? Dazu kann man eine globale Variable verwenden. Wenn diese als static gekennzeichnet ist, dann ist sie nur von Funktionen in der selben Quelltext Datei erreichbar. Um sie von außen lesbar zu machen böte sich eine getter-Funktion an.

Wenn du mehrere Instanzen dieser globalen Variablen brauchst, informiere dich über objektorientierte Programmierung. Dazu muss es micht zwingend C++ sein. Man kann auch in C objektorientiert programmieren. Jede Objektfunktion bekommt als ersten Parameter eine Struktur mit den Zustandsdaten der Objekt-Instanz übergeben.

#7575210
Lesenswert?

Toni E. schrieb:

Das Ergebnis wird aber auch in einer Struktur von modul1 gespeichert.

Ganz generell: Schreibe einen Code, der möglichst einfach genau Dein Problem schildert. Lass unnötige Kommentare weg, kürze lange Namen, aber mach es "rund", also prinzipiell lauffähig. Es ist (in diesem Fall) auch egal, ob es in einer oder n Dateien verteilt ist (Header und deren Verwendung sind ein Thema für sich).

Meinst Du z.B. so?

1
int modul2(int par)
2
{
3
   if(par == ... // verarbeite par
4
   ...
5
   return 2; // irgendein Rückgabewert
6
}
7

8
void modul1(void)
9
{
10
static int ergebnis;
11

12
   ergebnis += modul2(ergebnis);  
13
   if(ergebnis ... // was auch immer 
14
}
15

16
int main(void)
17
{
18
   for(;;)
19
   {
20
      modul1();
21
   }
22
}

Je nach Deiner eigentlichen Aufgabe kannst du auch einen Pointer verwenden. Oder (auch wenn man es nicht soll) eine globale Variable.

OP #7575920
Lesenswert?

Danke für die Tipps.

Eigentlich soll es quasi Objektorientiert sein, also Struktur wird als Pointer übergeben usw. Mein Problem ist wo lege ich die Struktur variable an in der while(1) schleife, in Modul 1? Und wird sie global angelegt oder wie?

1
typedef struct
2
{
3
 int zeit;
4
 int Ergebnis;
5
}zeitModul;
6
int modul2(int par)
7
{
8
   if(par == ... // verarbeite par
9
   ...
10
   return 2; // irgendein Rückgabewert
11
}
12
void modul1(Zeitmodul *zeiten)
13
{
14
static int ergebnis;
15
   Zeiten.Ergebnis += modul2(Zeiten.Ergebnis);  
16
   if(ergebnis ... // was auch immer 
17
}
18
int main(void)
19
{
20
 zeitmodul Zeiten; // hier oder in Modul 1?
21
   for(;;)
22
   {
23
      modul1(&Zeiten);
24
   }
25
}
#7576508
Lesenswert?

Toni, du solltest etwas mehr Sorgfalt auch in solchen "Überlegungscode" stecken. Drei Schreibweisen für "zeitModul". In C wird Groß-/Kleinschreibung beachtet, also achte darauf. Unten habe ich Deinen "Überlegungscode" kommentiert. Das sind einige Macken drin..

Achtung, du hast das Risiko eines "Seiteneffekts", wenn du eine Variable als Zeiger übergibst und den Rückgabewert wieder auf diese Variable speicherst.

Zur ursprünglichen Frage:

"wie mache ich nun das Ganze? Lege ich eine Globale Variable in der header von modul2 an? Oder mache ich das mit static in modul1?"

Welches ist die oberste Ebene auf der du die Variable benötigst? Wenn der höchste Geltungsbereich die Funktion "main" ist, dann reicht es sie innerhalb von main zu deklarieren. Brauchst Du sie noch in anderen Funktionen dieses Sourcecodes, dann halt auf Dateiebene.

Regeln:

  • Der Geltungsbereich einer Variablen sollte so klein als möglich gewählt werden.
  • Globale Variablen über Dateigrenzen hinweg nur im Notfall. Dann besser Zugriffsfunktionen.
1
typedef struct
2
{
3
   int zeit;
4
   int Ergebnis;  // Tipp: eimal groß, einmal klein --> sei gleich ordentlich und nutze eine Schreibweise...
5
} zeitModul;
6

7
int modul2(int par)
8
{
9
   if(par == ...)
10
   ...
11
   return 2; 
12
}
13

14
void modul1(Zeitmodul *zeiten) // ⚠️ Schreibfehler: "zeitModul"
15
{
16
   static int ergebnis;
17
   // ⚠️ Tippfehler: Der Parameter "zeiten" wird nicht genutzt. 
18
   // Es wird  eine globale "Zeiten" (großgeschrieben) Variable genutzt, die aber noch nicht bekannt ist...
19
   // ⚠️ Hier fehlt der Adressoperator "&Zeiten.Ergebnis"
20
   // ⚠️ Alarm: Seiteneffekt: Ergebnis könnte in Funktion "modul2" verändert werden. 
21
   Zeiten.Ergebnis += modul2(Zeiten.Ergebnis);  
22

23
   if(ergebnis ...) // ⚠️ ergebnis wird hier nicht genutzt...
24
}
25

26
int main(void)
27
{
28
   zeitmodul Zeiten; // ⚠️ Schreibfehler: "zeitModul"
29
   // ⚠️ Error: Variable ggf. falsch initialisiert
30
   for (;;)
31
   {
32
      modul1(&Zeiten);
33
   }
34
}

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren