Aufruf Funktion "return char c; & Parameterliste

Hallo in die Runde, klingt vielleicht bescheuert, aber ich knoble an folgendem Problem:
Einer Funktion sollen n Variable verschiedener Typen in der Parameterliste übergeben werden, die dann einen oder mehrere der Parameter irgendwie beharkt bzw. beharken und wenn sie durch ist einen Char von 0 ...125 zurückgeben.

Kann es sein, daß in eine Arduino Funktion der "return CHAR" eine besondere Vereinbarung bedarf, um zusammen mit einer Rückgabe-Parameterliste zu funktionieren
?
Denn ohne Parameterliste geht der "return CHAR", aber eben nicht mit.
Weiß jemand da Abhilfe?
Schönen Abend allerseits und schon mal Danke für Eure Hilfe.
Bavaricus

kannst Du das nochmal verständlich formulieren, was Du machen willst? Ab besten mit einem Beispiel - Was willst Du übergeben und was zurückgeben (wohl ein char)?

Gruß Tommy

Welchen Wert soll das zurückgeben?

Eine Definition könnte so aussehen:

char func(int a, char b)
{
   return b + a;
}

Mittels Return geht nur eine Variable als Rückgabewert, in deinem Fall wohl der char.

Wenn die Funktion eine Variable der Parameterliste ändert und den Wert dann zurück geben soll geht das als Referenz.


struct Return
{
  char c;
  int i;
};

Return func()
{
  return{'a',42};
}

void setup() 
{
  Serial.begin(9600);
  Serial.println(func().c);
  Serial.println(func().i);
}

void loop() 
{

}

Wenn @bavaricus durch @combie s Lösung verwirrt wird, ist das die gerechte Strafe für falsches Fragen.

  1. Vermutlich meint @bavaricus den Datentyp char (nicht CHAR)

  2. Den Datentyp des Rückgabewerts einer Funktion gibt man am Anfang, vor dem Funktionsnamen, an (nicht im return Statement)

  3. Eine Funktion, die alles mögliche kann, ist meist ein Design-Fehler.

Dies ist eine Glanzleistung meiner Glaskugel. Liegt eventuell komplett falsch, aber zeigt viel Einfühlungsvermögen in verwirrende und wohl auch verwirrte Gedankengänge.

Meine Glaskugel sagt:

  • [X] Wir haben hier ein X-Y Problem vor uns.
  • [X] Gepaart mit der Abwesenheit eines C++ Grundlagenbuches.
  • [X] Unklare Problem Beschreibung

Du bist der erste, der das Spetialpolierset "Arduino for Kristallkugel" bekommt. Gratuliere :wink: :wink: :wink:
Grüße Uwe

Muss aber feiner sein als AURORA Roggenmehl Type 1150.
Dock und... :rofl:

Hallo Rentner, hallo in die Runde,

den meisten haben wohl schon seit der Schule eine generalisierte Textaufgaben-Allergie. Es war eine ernst gemeinte Frage, in wieweit es in der Arduino-Sprach Umsetzung eine Einschränkung beim char geben könnte, zumal die Doku sagt:

Die Größe des char-Datentyps beträgt mindestens 8 Bit. Es wird empfohlen, char nur zum Speichern von Zeichen zu verwenden. Verwende für einen vorzeichenlosen 1-Byte-Datentyp (8 Bit) den byte-Datentyp.

Was ja nicht ausschließen würde, daß wie in C üblich, dann ein char auch ein Munis vertragen würde. Der Zahlenraum ist in der Docu nicht explizit genannt.

Da braucht man weniger herumflegeln, als mal nachzudenken, ob an der Frage was dran sein könnte.

Hintergrund ist die, bei alten C-Leuten gerne benutzte Strategie des error-Return eines Funktionswertes, zur weiteren Nutzung im aufrufenden Programm, gerne gleich mit entsprechender Error # oder aber eben gerne auch mal als -1.

In der Parameterliste stehen teilweise referenzierte und unreferenzierte Variable unterschiedlichen Typs, was nur auf die nachstehend beschriebene Ungereimtheit abzielt.

Ein Variablen TYPE „BYTE“ ist in C entweder

ein unsigned char mit 8 Bit also decimal 0 .. 255 oder
ein (signed) char mit 8 Bit mit 7 Bit für die „Zahl“ und ein Bit für das Vorzeichen

aber eben in jedem Fall 8 bit lang, wobei der Anwender sich drum kümmern muß was er damit macht.

Eigentlich ist nach ANSI C z.B. eine recht ausführliche Quelle ist das https://archive.org/details/micro-soft-c-5v-0-lang-ref Handbuch von 1984 die ich auch heute noch gerne zum Nachschauen nutze.

Auf Seite 51 steht zu Variablen Typen Fundamentals :
char 1 byte -128 .. 127
int Implementation depending (Arduino 16 Bit also 2 byte)

In der Arduino-Welt scheint der Type char aber einen Haken zu haben.
Nietet man per binärem ODER dem High Byte in sein High Bit eine „1“ , dann werden auf wunderbare Weise aber scheinbar 4 Byte verbraten! Siehe nachstehendes Beispiel.

char CHAR = 0b10000001;
int iCHAR = 0b10000001;
byte ax = 0b10000001;
Serial .println (" defined as: char CHAR = 0b10000001;");
Seria .print (" BIN CHAR = "); **Serial** .println (CHAR, BIN);
Serial .print (" int "); **Serial** .println(int (CHAR), DEC);
Serial .print (" sizeof(CHAR) as char = ");
Serial.print (sizeof(CHAR)); **Serial** .println (" byte");
Serial.println ();
Serial.println (" defined as: int iCHAR = 0b10000001;");
Serial.print (" BIN iCHAR = "); **Serial** .println (iCHAR, BIN);
Serial.print (" int "); **Serial** .println (int (iCHAR), DEC);
Serial.print (" sizeof(iCHAR) as int = ");
Serial.print (sizeof(iCHAR)); **Serial** .println (" byte");
Serial.println ();
Serial.println (" defined as: byte ax = 0b10000001;");
Serial.print (" BIN ax = "); **Serial** .println (ax, BIN);
Serial.print (" int "); **Serial** .println (int (ax), DEC);
Serial.print (" sizeof(ax) ax as byte = ");
Serial.print (sizeof(ax)); **Serial** .println (" byte");

Das wird dann zu:

defined as: char CHAR = 0b10000001;
BIN CHAR = 11111111111111111111111110000001
int -127
sizeof(CHAR) as char = 1 byte

defined as: int iCHAR = 0b10000001;
BIN iCHAR = 10000001
int 129
sizeof(iCHAR) as int = 2 byte

defined as: byte ax = 0b10000001;
BIN ax = 10000001
int 129
sizeof(ax) ax as byte = 1 byte

Beim CHAR-Beispiel meint der Sizeof es wäre 1 Byte lang, pinselt auf dem Serial Monitor aber 4 byte BINär raus.

Was richtigerweise -127 gibt, aber so war CHAR ja nicht vereinbart.

Lehre: will man eine Arduino function als return error einen Wert auf den Heimweg geben, sollte auf das Fehlen des 8ten Bits einer char-Variablen Rücksicht genommen werden, da eben die Implementation des Typs char beim Arduino keine negative werdende Zahl ermöglicht, da der Datentyp nur 7-Bit nutzt also sind nur Zahlen von 0 ... 127 möglich. Schade, würde Platz sparen.

Gruß Bavaricus

Das hängt einzig und allein vom aktuellen Datentyp ab. Wenn ein signed Wert an einen größeren Datentyp übergeben wird, dann wird dieser mit dem Vorzeichen aufgefüllt. Mit dem Testprogramm wird lediglich nachgewiesen, daß Serial.println(int32_t arg) definiert ist und daher als BIN bis zu 32 bits ausgibt.

Unfug!
Weder in C, noch in C++ ist die Größe von byte festgelegt, außer, dass ein char eben mindestens 8 Bit haben muss.

Natürlich ist ein total veraltetes C Buch die beste Wahl, wenn man C++ in der Version C++11 verwendet.
Sorry, aber das ist auch Unsinnig

Du hast dein C++ Buch nicht ordentlich gelesen!
Denn dann wüsstest du, dass char für Zeichen gedacht ist, und nicht zum rechnen.
Auch wüsstest du dann, dass das nichts mit Arduino zu tun hat.

Du castest ein char zum int, und wunderst dich, dass nicht das dabei raus kommt, was du dir wünscht.
Wieder: C++ Buch nicht gelesen.

Es war und ist eine unverständliche Frage!

Und du hast eine ganz offensichtliche DokuLeseHemmung.
Aber dafür eine rege Fantasie.

Das glaube ich Dir, aber auch eine für mich unverständliche.

Deine neuerlichen Ausführungen bringen nun etwas mehr Licht ins Dunkel. Wenn ich Dein Programm laufen lasse, bekomme ich dies:

 defined as: char CHAR = 0b10000001;
 BIN CHAR = 10000001
 int 129
 sizeof(CHAR) as char = 1 byte

 defined as: int iCHAR = 0b10000001;
 BIN iCHAR = 10000001
 int 129
 sizeof(iCHAR) as int = 4 byte

 defined as: byte ax = 0b10000001;
 BIN ax = 10000001
 int 129
 sizeof(ax) ax as byte = 1 byte

Ich kann nicht zaubern, sondern nutze einen ESP32, der als 32-Bitter ganz offensichtlich ein anderes Ergebnis liefert.

Meinst Du sowas?

void setup()
{
  Serial.begin(115200);
  delay(500);
  Serial.println("Start ...");
  int ergebnis = 0;
  if ( !rechne(ergebnis, 6, 2) )
  {
    Serial.println(ergebnis);
  } else {
    Serial.println("Fehler");
  }
  if ( !rechne(ergebnis, 6, 0) )
  {
    Serial.println(ergebnis);
  } else {
    Serial.println("Fehler");
  }
}

int8_t rechne(int &y, int a, int b)
{
  Serial.print(a);
  Serial.print('\t');
  Serial.print(b);
  Serial.print('\t');
  int8_t fehler = -1;
  if (b != 0)
  {
    y = a / b;
    fehler = 0;
  }
  return fehler;
}

void loop() {}

Das ist natürlich auch falsch!

In C und C++ gibt es eine Konstante CHAR_BIT welche dir sagt, wieviel Bit ein char hat.
Und diese Bit sind natürlich voll nutzbar!
Ohne jede Einschränkung. Nur halt nicht zum rechnen.

Wenn du mit char rechnen möchtest, solltest du "unsigned char" oder "signed char" verwenden.
Diese sind in den meisten Fällen mit int8_t oder eben mit uint8_t identisch.

Hallo agmue, ja so war es eigentlich gedacht. Danke.
Ich stamme noch aus einer Zeit, wo man ein Bit noch wirklich nutzen mußte, weil einfach nicht so viel Speicher verfügbar war.
Schönen Sonntag
Bavaricus

Das gilt bei den beliebten 8bit-Arduinos immer noch. 2kB RAM ist nun wirklich nicht viel. Ist eher faszinierend, wie viel man damit machen kann.

Was allerdings deine Ausführungen zu ANSI-C mit Arduino zu tun haben, verstehe ich immer noch nicht. Die "Arduino-Sprache" ist C++ mit ein paar unnötigen Zusatz-Definitionen (boolean). Ein byte ist identisch zu uint8_t definiert.

combie, natülich ist das alles falsch ... und dann auch noch ein Buch aus dem Antiquariat zurate zu ziehen ... Gott ach Gott, ... wie kann man nur !?! Freilich bleibst Du uns allen die "echte C/C++" Bibel Deiner Programmierer-göttlich unerschöpflichen Weisheit zu benennen, schuldig.
Vorlesen willst' se ja auch nicht.

War lange schon am überlegen, weshalb Germany dermaßen am absteigenden Ast ist. Du hast mir die Antwort gegeben!

@all Ich hatte die kollegiale Naivität, daß man in diesem Forum Fragen, und seien es vermeintlich die dämlichsten, höflich stellen können "darf". Du magst ja ein super guter Programmierer sein. Mein Bester, in meinem Unternehmen hättest Du keine 5 Minuten im Bewerbungsgespräch überlebt. Überhebliche Arroganzlinge habe ich reihenweise aussortiert. Die Erfahrung lehrt, wer dermaßen auf die Kacke haut, indem er einen anderen in die Pfanne hauen muß, ist schlicht für Professionelles jeglicher Art in der echten Welt zu nichts zu brauchen.
Bavaricus

Der Einzige, der hier arrogant labert bist doch Du. So erhöhst Du die Hilfsbereitschaft ungemein.
Für meinen Teil sage ich dann:

Und Tschüß
Gruß Tommy

Darf man natürlich. Man darf auch Unsinn von sich geben, wie deine 7 Bit bei einem char Datentyp.
Man muss nur ertragen, dass sowas nicht unwidersprochen bleibt.
Und wenn einem mehrfach Unverständlichkeit rückgemeldet wird, besteht die Wahrscheinlichkeit, dass da was dran ist.

Dass @combie rückgemeldet kriegt, wie er wirkt, ist ihm auch schon vorgekommen. Das muss er (in Grenzen) aushalten :wink:

1 Like

Fragen dürfen ruhig auch mal dämlich sein, aber falsche Behauptungen so wie Deine ganz sicher nicht:

Das kann nicht unwidersprochen bleiben! Und wenn Du dann auch noch versuchst, Dich irgendwie herauszuwinden, statt einfach Deinen Fehler einzugestehen, dann kommt das verständlicherweise garnicht gut an.

Das ist ein persönlicher Angriff, der selbst nach Deiner Meinung:

kaum zu tolerieren.

Also kommt jetzt bitte runter und redet nur noch über Fakten und nicht über Personen.