Forum: Mikrocontroller und Digitale Elektronik C++: Mehrere Funktionen Zugriff auf Variable


von Anfänger C++ (Gast)


Lesenswert?

Ich hatte vor ein paar Tagen schon einmal eine ähnliche Frage gestellt. 
Für mich als C++ Anfänger nicht so leicht zu bewerkstelligen.

Szenario:
Ich verarbeite in einer Funktion1 eine bestimmte Variable und weise ihr 
einen Wert zu. Genau diese Variabe möchte ich mit dem in Funktion1 zu 
gewiesenen Wert in einer Funktion2 wieder nutzen. Ich habe jetzt einiges 
bzgl. globaler Variablen und call by Reference durchgelesen un einiges 
ausprobiert. Es hat jedoch nie richtig kompiliert. Vermutlich weil ich 
mit der richtigen Syntax nicht vertraut bin. Über ein richtiges Beispiel 
wäre ich dankbar.

Minimalbeispiel_
1
void funktion1()
2
{
3
 int x;
4
 x = 21;
5
}
6
7
void funktion2()
8
{
9
 int y;
10
 y = 2*x;  // <- hier soll x automatisch gleich 21 sein, 
11
// d.h.funktion1()muss natürlich vor funktion2() aufgerufen werden
12
}

Greetz

von Thomas E. (thomase)


Lesenswert?

Anfänger C++ schrieb:
> Minimalbeispiel_
> void funktion1()
> {
>  int x;
>  x = 21;
> }
>
> void funktion2()
> {
>  int y;
>  y = 2*x;  // <- hier soll x automatisch gleich 21 sein,
> // d.h.funktion1()muss natürlich vor funktion2() aufgerufen werden
> }

Nicht VOR sondern VON.
1
int f1()
2
{
3
  int x = 21;
4
  return x;
5
}
6
7
void f2()
8
{
9
  int y = 2 * f1();
10
}

mfg.

von Marcel (Gast)


Lesenswert?

1
int x;

Global definieren anstatt lokal in einer Funktion. Da kann man 
eigentlich nichts falsch machen. Wo gab es hier Syntaxfehler?

Oder
1
int funktion1()
2
{
3
 int x;
4
 x = 21;
5
 return x;
6
}

In funktion2 dann einfach funktion1 aufrufen und den Wert abholen.

Welche Lösung davon besser ist geht aus deinem Minimalbeispiel nicht 
hervor.

von guest (Gast)


Lesenswert?

und was ist mit static?

von Marcel (Gast)


Lesenswert?

guest schrieb:
> und was ist mit static?

static sorgt dafür, dass lokale Variablen auch nach dem beenden der 
Funktion im Speicher bleiben.

von Anfänger C++ (Gast)


Lesenswert?

Ich würde gerne mehrere Variablen in Funktion1() nutzen. DIe Möglichkeit 
mit die Variable als Rückgabewert wiederzuverwenden liegt also auf Hand, 
fällt bei mir jedoch aus.

Wie genau funktioniert dies mit en globalen Variablen?
In etwa so?
1
unter.h
2
extern int x;
3
extern int y;
4
extern int z;
5
void funktion1();
6
void funktion2();
7
8
unter.c
9
void funktion1()
10
{
11
 x = 21;
12
 y = 13;
13
 z = 33;
14
}
15
16
void funktion2()
17
{
18
 int a,b,c;
19
 a = 2*x;  
20
 b = a + 2*y;
21
 c = z;
22
}

Irgendwoe ist da noch nen Fehler drin!

von Oliver S. (oliverso)


Lesenswert?

Vielleicht wäre es jetzt Zeit für ein C-Buch. Das ++ kannst du getrost 
weglassen, deine Fragen haben C++ nix zu tun.

Oliver

: Bearbeitet durch User
von Cube_S (Gast)


Lesenswert?

lass das "extern" weg und packe das

int x, y, z;

in "unter.c"

von C Plus Plus (Gast)


Lesenswert?

C++ und globale Variablen machen keinen Sinn. Ein wichtiger Bestandteil 
von OOP ist die Datenkapselung. Man sollte daher nicht von Variablen 
sprechen, sondern von Objekten und Eigenschaften. Eigneschaften erreicht 
man nicht direkt.

von Cube_S (Gast)


Lesenswert?

Man muss hier die Kirche im Dorf lassen. Auch bei objektorientierter 
Programmierung wird man um globale Variablen nicht immer herumkommen. Da 
heißen sie dann "ganz wichtigtuerisch" Singletons, sind aber im Prinzip 
nichts anderes als stinknormale globale Variablen.

Je nach Anwendung also absolut vertretbar.

von alter Hut (Gast)


Lesenswert?

Cube_S schrieb:
> Auch bei objektorientierter
> Programmierung wird man um globale Variablen nicht immer herumkommen.

Dann hast du OOP nicht verstanden.

von Cube_S (Gast)


Lesenswert?

alter Hut schrieb:
> Dann hast du OOP nicht verstanden.

Das halte ich für ein Gerücht

von Anfänger C++ (Gast)


Lesenswert?

Cube_S schrieb:
> lass das "extern" weg und packe das
>
> int x, y, z;
>
> in "unter.c"

Das habe ich so versucht. Leider haben die Variablen in Funktion2 nicht 
den Wert, den ich Ihnen in Funktion1() zugewiesen habe.

Hab es debuggt.

Alternativen?

von Roland (Gast)


Lesenswert?

Cube_S schrieb:
> ...GLobale Variablen...
>
> Je nach Anwendung also absolut vertretbar.

Nein. Globale Variablen sind nie vertretbar.

von Anfänger C++ (Gast)


Lesenswert?

Ich wäre trotzdem für Anregungen für das Lösen meines Problems dankbar 
:)

von einfach mal die Antworten lesen (Gast)


Lesenswert?

Deine C (und nicht C++) Frage wurde bereits beantwortet.

Entweder nimmst du die schlechte Lösung mit globalen Variablen oder 
nutzt Parameter und Rückgabe werte von Funktionen.

von "Dr. Sommer" würde sagen (Gast)


Lesenswert?

> Ich verarbeite in einer Funktion1 eine bestimmte Variable und weise ihr
> einen Wert zu. Genau diese Variabe möchte ich mit dem in Funktion1 zu
> gewiesenen Wert in einer Funktion2 wieder nutzen.

Entscheide dich erstmal, ob du C oder C++ programmieren möchtest !

Lösung in C:

f1() erzeugt ein Datum, gibt Datum via return zurück
f2() nimmt Datum von f1() als Parameter auf, führt Berechnung aus und 
gibt seinerseits Datum zur Ausgabe an ein printf zurück

Lösung in C++:

Baue dir eine Klasse K1, die ein Datum (eine private Membervariable) m1
und zwei öffentlichen Methoden f1(), f2() besitzt.
Instanziere ein Objekt dieser Klasse, dass nacheinander die Methoden 
f1() und f2() aufruft

f1() wirkt auf m1 ein
f2() wirkt auf m1 ein

Dann baust du dir noch eine Methode zur Ausgabe(), die als drittes 
aufgerufen wird.

von Cube_S (Gast)


Lesenswert?

1
static int x, y, z;
2
3
void funktion1()
4
{
5
  x = 21;
6
  y = 13;
7
  z = 33;
8
}
9
10
void funktion2()
11
{
12
  int a, b, c;
13
  a = 2 * x;
14
  b = a + 2 * y;
15
  c = z;
16
}
Wenn es so nicht funktioniert, hat dein Compiler ein Problem. Das 
"static" ist nicht zwingend, macht die Variablen aber für andere 
c-Quelldateien beim linken "unsichtbar".

von Cube_S (Gast)


Lesenswert?

Für diejenigen, die es unbedingt "objektorientiert" sehen wollen:
1
class A
2
{
3
private:
4
  int x, y, z;
5
6
public:
7
  void funktion1();
8
  void funktion2();
9
};
10
11
void A::funktion1()
12
{
13
  x = 21;
14
  y = 13;
15
  z = 33;
16
}
17
18
void A::funktion2()
19
{
20
  int a, b, c;
21
  a = 2 * x;
22
  b = a + 2 * y;
23
  c = z;
24
}
25
26
int main()
27
{
28
  A a;
29
  a.funktion1();
30
  a.funktion2();
31
  return 0;
32
}
Wobei ich die Kapselung alleine noch nicht als Objektorientierung 
bezeichnen würde. Dieser Begriff ist meiner Meinung nach erst dann 
wirklich gerechtfertigt wenn die "späte Bindung" ins Spiel kommt. Also 
mindestens zwei Klassen die von einander erben vorhanden sind und die 
Basisklasse eine virtuelle Funktion hat, die in der abgeleiteten Klasse 
überschrieben wird.

von Cube_S (Gast)


Lesenswert?

Der Vollständigkeit halber noch "call by reference" im klassischen 
C-Stil
1
void funktion1(int *x, int *y, int *z)
2
{
3
  *x = 21;
4
  *y = 13;
5
  *z = 33;
6
}
7
8
void funktion2(int x, int y, int z)
9
{
10
  int a, b, c;
11
  a = 2 * x;
12
  b = a + 2 * y;
13
  c = z;
14
}
15
16
int main()
17
{
18
  int x, y, z;
19
  funktion1(&x, &y, &z);
20
  funktion2(x, y, z);
21
  return 0;
22
}

von Bastler (Gast)


Lesenswert?

Anfänger C++ schrieb:
> Cube_S schrieb:
>> lass das "extern" weg und packe das
>>
>> int x, y, z;
>>
>> in "unter.c"
>
> Das habe ich so versucht. Leider haben die Variablen in Funktion2 nicht
> den Wert, den ich Ihnen in Funktion1() zugewiesen habe.
>
> Hab es debuggt.
>
> Alternativen?

Dir ist aber schon klar, daß Funktion1 erst mal gerufen werden muß, 
damit sie irgend einen Einfluß auf x,y,z haben kann, oder?

von Jan K. (jan_k)


Lesenswert?

Hi Leute, ich habe ne frage zu dem letzten Beispiel (call by reference). 
Warum sollte man das so machen? Sehen und verändern können ja eh beide 
Funktionen die variablen. Auch ohne call by reference... Macht man das 
dann rein zu Übersichtzwecken?

Ich frage, weil ich ganz konkret vor einer Implementierung stehe, bei 
der ein Modul (eine C datei)  über ziemlich viele "lokale"  (static) 
variablen verfügt. Wäre schön ein ziemlicher Aufwand, die immer zu 
übergeben.  Dafür sieht man, was in welcher Funktion benötigt wird.
Oder ist es eh ratsam, ein neues typedef für das Modul zu machen, das 
eine struct ist, die alle lokalen Variablen enthält und dann in "c++ in 
c" Art, sprich manuelle Übergabe des "objektes" an die öffentlichen 
Funktionen zu machen?

Danke und schöne Grüße,
Jan

von Cube_S (Gast)


Lesenswert?

Jan K. schrieb:
> Sehen und verändern können ja eh beide
> Funktionen die variablen. Auch ohne call by reference

Verändern kann in diesem Beispiel nur "funktion1". Ob man das so machen 
sollte ist eine andere Frage. Sobald die Parameterlisten ausarten ist 
schon zu überlegen ob diese Parameter von der Sache her nicht ein Objekt 
darstellen und die von Dir vorgeschlagene Lösung mit dem "struct" oder 
in C++ dann "class" nicht die bessere Variante ist.

von Karl H. (kbuchegg)


Lesenswert?

Jan K. schrieb:
> Hi Leute, ich habe ne frage zu dem letzten Beispiel (call by reference).
> Warum sollte man das so machen?

Weil man im allgemeinen möglichstr wenig globale Variablen haben will. 
Bei kleinen µC muss bzw. wird man da ein wenig Abstriche machen, weil es 
da ein anderes Problem gibt. Auf den kleinen µC muss man den 
Speicherverbrauch in Summe im Auge behalten und das geht mit globalen 
Variablen am einfachsten.

Aber ansonsten will man zb für einfache und simple Standardaufgaben 
keine globalen Variablen haben, weil das Buchführen welcher Wert jetzt 
gerade in der globalen 'Interface' Variablen sitzt mühsam und 
fehleranfällig ist.

> Funktionen die variablen. Auch ohne call by reference... Macht man das
> dann rein zu Übersichtzwecken?

Du kriegst dann eine Funktion die auch wirklich in sich abgeschlossen 
ist und keine Nebeneffekte an irgendwelchen globalen Variablen hat. Die 
Funktion kann dann von jeder Stelle aus bedenkenlos aufgerufen werden. 
Sie macht ihr Ding, liefert ihre Werte und das wars.

> Ich frage, weil ich ganz konkret vor einer Implementierung stehe, bei
> der ein Modul (eine C datei)  über ziemlich viele "lokale"  (static)
> variablen verfügt.

Welches Modul?

>  Dafür sieht man, was in welcher Funktion benötigt wird.
> Oder ist es eh ratsam, ein neues typedef für das Modul zu machen, das
> eine struct ist, die alle lokalen Variablen enthält und dann in "c++ in
> c" Art, sprich manuelle Übergabe des "objektes" an die öffentlichen
> Funktionen zu machen?

Das kommt drauf an.
Wenn du das Gefühl hast, das es sich dabei um ein tatsächliches 'Objekt' 
handelt ... ja dann würde man das genau so machen.

Ein Stack beispielsweise, oder eine FIFO ist für sich genommen ein 
'Objekt' mit einer für sich alle vernünftigen Funktionalität. Zudem ist 
das etwas, das man immer wieder mal gebrauchen kann. D.h. in dem Fall 
würde man sehr wahrscheinlich die ganze Sache sauber machen und alle 
Variablen, die du jetzt als (static) modul-lokale globale Variablen 
eingeführt hast, in einer struct organisieren. Im Endeffekft ist das ja 
nichts anderes als eine andere Origanistation, in der um die (stativ) 
modul-lokalen Variablen eine Hülle gelegt wird und ihnen ein Name 
gegeben wird.

Das 'löst' dann gleich auch deine Bedenken wegen der langen 
Argumentlisten. Anstelle alle 'Variablen' einzeln zu übergeben, stellst 
du den Funktionen einen Pointer auf das Objekt zur Verfügung, mit denen 
sie arbeiten sollen. Und plötzlich ist es dann auch überhaupt kein 
Problem mehr, mit ein und demselben Satz von Funktionen nicht nur 1, 
sondern auch schon mal 4 derartige FIFO Objekte in einem Programm zu 
haben.

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.