Forum: Mikrocontroller und Digitale Elektronik c coding conventions?


von oskar aus der mülltonne (Gast)


Lesenswert?

Gibt es sowas wie universelle Coding Conventions oder Richtlinien im 
µC-Bereich. Also, so wie ich das gesehen habe, verwendet jeder 
Hersteller eigene Regeln und selbst in unteschiedlichen AppNotes, x, y, 
.. gibt es noch Unterschiede. (Es geht mir nicht um guten Stil, sondern 
um whitespaces usw.)

Gibt es da irgendwas verbreiteteres? K&R? GNU? 2, 4, oder 8 indents? 
(oder gibt es hier auch verrückte kauze, die mit 3 oder 5 einrücken?)
oder tabs?

Und wie sieht es mit den Bezeichnern aus? Ich habe mich an 
'zwei_worte()' gewöhnt. gibt es leute die ZweiWorte, oder zweiWorte, 
oder Zwei_Worte oder andere Varianten präferieren? und wenn ja, wie 
zahlreich seid ihr?

Evtl. noch unterschiedliche Bezeichnerstile für Variablen und 
Funktionen?

Makros immer GROSS oder nur die KONSTANTEN_MIT_UNTERSTRICHEN oder 
makro-funktionen so wie in der avrlibc nach_diesem_stil() ?

Wie sehen newlines in funktionsaufrufen/definitionen bei euch aus?

beste grüße,
oskar_ausDerMülltonne();

von oskar aus der mülltonne (Gast)


Lesenswert?

Soweit ich weiß definiert MISRA-C in der Richtung nichts, richtig?

und Yoda-Conditions - ja oder nein?

(heißt if (5 == a) anstelle von if (a == 5) - vermeidet versehentliche 
verwendung des zuweisungsoperators)

von Yalu X. (yalu) (Moderator)


Lesenswert?

oskar aus der mülltonne schrieb:
> Gibt es da irgendwas verbreiteteres? K&R? GNU?

Von GNU gibt es das

  http://www.gnu.org/prep/standards/standards.html

von anderen wieder anderes.

Es führt leider kein Weg daran vorbei, sich öfters an neue Programmier-
richtlinien zu gewöhnen, je nachdem in welchem Umfeld man arbeitet.

von oskar aus der mülltonne (Gast)


Lesenswert?

zb das hier
     if (foo)
       ...
     else
       {
         if (bar)
           ...
       }

die 2 spaces vor den klammern finde ich persönlich zum kotzen.

die sache ist halt die, das fast jeder schnipsel code den man irgendwo 
findet anders aussieht. entweder man hat dann am ende einen hässlichen 
haufen code, oder man muss alles neu schreiben / refaktorieren.

deswegen die frage nach generell akzeptierten coding conventions...

ich glaube sogar hier im wiki sieht alles anders aus. macht es nicht 
sinn sich da mal festzulegen? warum ist sowas nicht im rahmen von 
MISRA-C z.B. geschehen?

von Vlad T. (vlad_tepesch)


Lesenswert?

oskar aus der mülltonne schrieb:
> die sache ist halt die, das fast jeder schnipsel code den man irgendwo
> findet anders aussieht. entweder man hat dann am ende einen hässlichen
> haufen code, oder man muss alles neu schreiben / refaktorieren

warum?
im visual studio: text markieren strg+k, strg+f
im eclipse: strg+shift+f
und schon hat man fertig formatierten Code.

unter eclipse kann man die gewünschte Zielformatierung sogar sehr 
detailiert einstellen.

von Mark B. (markbrandis)


Lesenswert?

oskar aus der mülltonne schrieb:
> warum ist sowas nicht im rahmen von MISRA-C z.B. geschehen?

Vielleicht weil MISRA-C nur für den Automobilbereich wirklich 
verbindlich ist? Anderen steht es frei, sich ebenfalls daran zu halten - 
sie müssen es aber nicht...

von Karl H. (kbuchegg)


Lesenswert?

So ziemlich die einzige Konvention, an die sich alle halten, lautet:
Namen ausschliesslich in Grossbuchstaben, sind für Makros reserviert.

von oskar aus der mülltonne (Gast)


Lesenswert?

ok, ich merke schon ich stoße hier auf unverständnis, aber ich finde es 
nicht schön auf 'hässlichen' code zu treffen alleine nur wenn ich ihn 
lesen MÖCHTE.

und @vlad tepesch: genau das ist refactoring. schön das vs und eclipse 
das automatisch machen. aber das müsste doch gar nicht nötig sein.

MISRA-C war nur ein beispiel. vllt. sogar unpassend.

wenn das thema anscheinend niemand interessiert, dann kann man es ja 
auch wieder verwerfen und jeder macht was er will.

von Vlad T. (vlad_tepesch)


Lesenswert?

misra enthält aber auch viel Blödsinn, der eher zusätzliche Fehler 
provoziert.

zB das Funktionen nur ein Return statement haben sollen, oder dass eine 
Schleife maximal ein break haben darf.
Beides führt zu undurchsichtigen If-Konstrukten, die außerdem der 
Performanz abträglich sind.

Was zum Beispiel Schlimm daran am Anfang einer Funktion ein paar 
Eingangswerte abzutesten und gebenenfalls die Funktion zu verlassen.
Stattdessen muss man den kompletten body der Funktion in eine 
zusätzliche Verschachtelungsebene packen.

Oder wenn im Laufe der Abarbeitung einer Schleifeniteration es mehrere 
mögliche Exitpoints geben kann, in dem entweder die aktuelle Iteration 
oder die ganze Schleife abgebrochen werden muss.
1
int sum = 0;
2
for(i=0;i<500;++i)
3
{
4
   int e1;
5
   int e2;
6
   int e3;
7
   e1 = berchnung1;
8
   if( 0==e1 ){
9
     break;
10
   }
11
   
12
   e2 = berchnung2;
13
   if( 0==e2 ){
14
     continue;
15
   }
16
17
   e3 = berchnung3;
18
   if( 0==e3 ){
19
     break;
20
   }
21
   sum +=e3;
22
}

wird zu:

1
for(i=0;i<500;++i)
2
{
3
   int e1;
4
   int e2;
5
   int e3;
6
   bool doBreak = false;
7
   e1 = berchnung1;
8
   if( 0==e1 ){
9
     doBreak = true;
10
   }else{
11
     e2 = berchnung2;
12
     if ( 0!=e2 ){
13
       e3 = berchnung3;
14
       if( 0==e3 ){
15
         doBreak = true;
16
       }else{
17
         sum +=e3;
18
       }
19
20
     }
21
  }
22
  if(doBreak){
23
    break;
24
  }
25
}

oder noch schlimmer, weil zusätzliche unbenötigte globalere Variable:
1
bool doBreak;
2
for(i=0; (i<500) && (!doBreak);++i)
3
{
4
   int e1;
5
   int e2;
6
   int e3;
7
   doBreak = false;
8
   e1 = berchnung1;
9
   if( 0==e1 ){
10
     doBreak = true;
11
   }else{
12
     e2 = berchnung2;
13
     if ( 0!=e2 ){
14
       e3 = berchnung3;
15
       if( 0==e3 ){
16
         doBreak = true;
17
       }else{
18
         sum +=e3;
19
       }
20
21
     }
22
  }
23
}


Jetzt fehlt mir hier nur noch einer, der sagt, das zweite wär leichter 
verständlich.

(ich hoffe ich habe bei der Umstellung nach MISRA nicht auch noch Fehler 
eingebaut)

von oskar aus der mülltonne (Gast)


Lesenswert?

Karl heinz Buchegger schrieb:
> Namen ausschliesslich in Grossbuchstaben, sind für Makros reserviert.

wobei das allerdings auch nur auf konstanten konsquent zutrifft. die 
avrlibc zb. bricht damit ja schon durch die zahlreichen makros wie 
boot_rww_busy().

von Vlad T. (vlad_tepesch)


Lesenswert?

Vlad Tepesch schrieb:
> code

berechnung1, berechnung2 und berechnung3 sollen natürlich funktionen 
sein, es fehlen also die Ellipsen.
Ich denke es wird trotzdem klar, was ich meine.

von Vlad T. (vlad_tepesch)


Lesenswert?

oskar aus der mülltonne schrieb:
> wobei das allerdings auch nur auf konstanten konsquent zutrifft. die
> avrlibc zb. bricht damit ja schon durch die zahlreichen makros wie
> boot_rww_busy().

macht ja auch Sinn, wenn es von außen halt wie eine normale Funktion 
aussehn soll, der Performance halber aber als Macro implementiert wurde.

wobei ich da lieber static inline funktionen bevorzugen würde, da sind 
argumente wenigstens typsicher.

von Falk B. (falk)


Lesenswert?


von oskar aus der mülltonne (Gast)


Lesenswert?

Vlad Tepesch schrieb:
> (ich hoffe ich habe bei der Umstellung nach MISRA nicht auch noch Fehler
> eingebaut)

das continue hast du ja wunderbar gelöst ;) ja das ist natürlich nicht 
einfacher zu lesen und diese regel verfehlt sicherlich ihr ziel, aber 
wie gesagt, MISRA-C wollte ich gar nicht jetzt konkret in die pflicht 
nehmen sondern nur als beispiel für eine weitverbreitete "vereinbarung" 
hernehmen.

von oskar aus der mülltonne (Gast)


Lesenswert?

Vlad Tepesch schrieb:
> macht ja auch Sinn, wenn es von außen halt wie eine normale Funktion
> aussehn soll, der Performance halber aber als Macro implementiert wurde.
>
> wobei ich da lieber static inline funktionen bevorzugen würde, da sind
> argumente wenigstens typsicher.

mMn sind inline-funktionen makros immer vorzuziehen und evtl auch noch 
performanter, wenn der compiler z.B. entscheidet nicht zu inlinen. wobei 
das bei timing-kritischen funktionen natürlich nicht passieren sollte. 
vor allem auch wenn das makro nur asm enthält ist doch eine inline 
funktion durchaus angebrachter. aber wie gesagt kommt auf den compiler 
an, bzw. inwieweit man die möglichkeit hat, da noch an schraueben ala 
force-inline zu drehen.

(ich glaube MISRA sagt zu makros auch was, oder? - finde die regeln 
grade auf die schnelle nicht... ich meine das war sowas wie alle makros 
nur für konstanten, dann immer alle buchstaben groß und funktionen 
sollen inline sein, sowie das für inline asm immer dedizierte funktionen 
verwendet werden müssen. damit wäre doch dann die avrlibc MISRA 
untauglich. wobei ich sowieso nicht glaube, dass jemand der MISRA-C 
erfüllen muss mit avrlibc arbeiten würde.)

von oskar aus der mülltonne (Gast)


Lesenswert?

Falk Brunner schrieb:
> Siehe Strukturierte Programmierung auf Mikrocontrollern


das ist doch schonmal ein anfang.. ich weiß das ist vllt. ein bisschen 
kleinkariert, aber was ist denn zum beispiel mit funktionsaufrufen:

Funktion ( param1,param2 );
Funktion(param1, param2);
Funktion (param1, param2);

oder switch:
1
switch(var) {
2
    case 5: { xy; break; }
3
}
4
oder vielleicht so:
1
switch ( var )
2
  {
3
    case 5:
4
      {
5
        xy;
6
        break;
7
      }
8
  }
oder gemischt:
1
switch (var) {
2
    case 5: {
3
                xy;
4
                break;
5
            }
6
}

den meisten wird das scheiß egal sein, aber es gibt wohl doch 
menschen/projekte die sehr viel wert auf so etwas legen, auch nicht nur 
im µC-Bereich.

von Tom (Gast)


Lesenswert?

Viele Firmen haben deswegen für sich Coding-Conventions festgelegt, z. 
B. 4 Leerzeichen Absatz, camelCase, Kommentare mit //, testweise 
auskommentieren mit /*, welche Dinge / Funktionen man lassen sollte, ...

Meistens dann auch für jede Programmiersprache extra...

von Karl H. (kbuchegg)


Lesenswert?

oskar aus der mülltonne schrieb:
> ok, ich merke schon ich stoße hier auf unverständnis,

Nicht wirklich.
Wir verstehen schon, was du wissen willst.

Der Punkt ist einfach nur:
Es gibt eine Unzahl an Konventionen. Such dir eine aus und halte dich 
daran.

Das ist nämlich das Wichtigste bei all diesen Konventionen:
Sei konsequent!

> aber ich finde es
> nicht schön auf 'hässlichen' code zu treffen alleine nur wenn ich ihn
> lesen MÖCHTE.

Da wirst du aber durch müssen.
Es ist nicht ungewöhnlich, dass man sich fremden Code, sofern man das 
darf, auf seine eigenen Konventionen zurechtschnitzt.

Wenn du in eine Firma kommst, dann werden dir dort sowieso die 
Firmenstandards aufs Auge gedrückt, an die du dich halten musst.

Ach ja, eines noch:
Wenn du es deinem 'Nachleser' einfacher machen willst, dann stellst du 
deinen Editor so ein, dass er Tabulatoren durch Leerzeichen ersetzt. 
Denn auch hier gibt es keinen Standard :-) Bei dem einen ist ein Tab 
gleich 2 Leerzeichen, beim nächsten 4 und dann wiederrum hat einer 8 
Leerzeichen als einen Tab. Kriegt man dann Code der nicht der eigenen 
Tab-Konvention unterliegt, ist es mit den Einrückungen Essig.

> wenn das thema anscheinend niemand interessiert, dann kann man es ja
> auch wieder verwerfen und jeder macht was er will.

Das tut er sowieso, bzw. es wird ihm vorgeschrieben.

Das einzige worin sich alle Standards in einem gewissen Sinne einig 
sind: Dicht gedrängter Code ala 'wir schonen die Leerzeichentaste' ist 
bäh. Ober wo nun genau die Leerzeichen sitzen sollen - such dir was aus 
was dir gefällt und womit du zurecht kommst.

von High Performer (Gast)


Lesenswert?

>Funktion ( param1,param2 );
>Funktion(param1, param2);
>Funktion (param1, param2);

Da geht's schon los: ich habe früher(TM) die Deklaration so geschrieben

void funktion (int a);

und den Aufruf dann funktion(4);

warum? Weil ich der Meinung war, dass das Leerzeichen in der Deklaration 
den Funktionsnamen freistellt und dieser dadurch schneller lesbar ist. 
Da die Deklarationen ja zumeist in Headern stehen, hat man in der Liste 
einen besseren Überblick über die Namen.

Beim Aufruf ist es dann besser, den Namen und die Argumente beieinander 
zu haben. Hier war ich lange Jahre konsequent inkonsequent.
Habe ich aber inzwischen aufgegeben, da sowas keinerlei 
Programmierrichtlinie entspricht - leider. Heute mache ich auch in der 
Deklaration kein Leerzeichen mehr.

Ich habe auch immer drei Zeichen eingerückt, obwohl das absolut unüblich 
ist. Ich verstehe auch heute noch nicht, warum es unbedingt vier sein 
müssen. Aber alle machen es so, also halte ich mich inzwischen auch 
dran.

Was ich mir nicht abgewähnen kann, ist, den Rückgabewert in einem return 
statement zu klammern. Für mich sieht das einfach grausam aus,
return 5; zu lesen statt return(5);

Ist aber wohl auch Gewohnheit.

Aber wenn solche Dinge eine Rolle spielen, ist man IMHO schon recht 
ordentlich beim Aufbau des Quelltextes. Ich sehe oft Quelltexte, die 
sehen einfach grausam aus und halten sich an keinerlei Konvention. Das 
kommt vor allem dann vor, wenn Ingenieure, die nicht unbedingt die 
absoluten Informatik-Profis sind, Quelltexte schreiben, z.B. für 
kleinere Tools oder uC. Aber zum Glück gibt es brauchbare refactoring 
tools, z.B. in eclipse.

von High Performer (Gast)


Lesenswert?

Nachträge:

auch wenn if (5 == a) sicherer ist als if (a == 5), verwende ich dennoch 
stets die zweite Variante. Und zu den Blöcken:

if (a == 5)
{
    printf("a == 5\n");
}


switch (a)
{
    case 1:
        printf("1\n");
        break;

    case 2:
        printf("2\n");
        break;

    default:
        break;
}


Auch in Java rücke ich so ein, wenn erlaubt, obwohl in Java absolut 
unüblich. Ich finde es so einfach am übersichtlichsten und halte es sein 
den Anfängen meiner Programmiertätigkeit so.

von oskar aus der mülltonne (Gast)


Lesenswert?

Tom schrieb:
> testweise
> auskommentieren mit /*

das ist verboten nach MISRA-C <- lol!

ok, danke, dann werde ich einfach so weitermachen wie bisher und meinen 
code in 1TBS schreiben. viel spaß beim refactoring!

von byte (Gast)


Lesenswert?

Vlad Tepesch schrieb:
> Jetzt fehlt mir hier nur noch einer, der sagt, das zweite wär leichter
> verständlich.

Ich für mich hab die Feststellung gemacht das Programme/Funktionen die 
mit nur jeweils einem Brake/Return gemacht wurden, wesentlich "robuster" 
beim Überarbeiten und Weiterentwickeln sind. Bzw. ich bin der Fan von 
strikter Kapselung der Abläufe. (Kein Undefinierter Zustand möglich) 
Insbesondere bei komplexen Großprojekten kommt immer wider mal vor das 
Jemand ein Brake rauswirft weils nicht mehr gebraucht wird, damit aber 
ungeahnte Kettenreaktionen auslöst. (Liegt mitunter auch an den großen 
Funktionen) Böserweise Fehler, die oft nicht gleich auffallen. Ist das 
Zeug gekapselt kann sowas i.d.Regel nicht passieren, bzw. läuft nicht 
unkontrolliert in irgendwelche Codeteile rein. Aber ganz ehrlich.. 
grundsätzlich hängts von der "Fähigkeit" des Programierers ab. Machen 
kann man beides... auch gut/schnell/übersichtlich. Manche Codeteile 
"Brake" ich auch (mit extra Kommentar), weils schlichtweg den Code 
verzehnfachen würde. Aber grundsätzlich => nur ein Return/Brake wenn 
möglich mach am wenigsten Probleme. Wenn man das konsequent durchzieht 
ist man selber oft überrascht was ein gut strukturierer Code alles von 
selber abfängt.

Allgemein zum Thema... ich bin beim Form und Dokumentation sehr strikt. 
Kenns so von meinen PHP-Projekten. Da is alles genau geregelt (Notation, 
etc) und auch die Dokumentation nach PHPDocumentor bzw. Javadoc. Was ich 
bei den uC Projekten so gesehen habe benutzt das wohl keiner, kann das 
sein? Ich find die generierten Dokus (Doxygen, documentor) aber immer 
sehr hilfreich. Gibts hier keine Standartvorgehensweise bei uCs? Dass 
kann man auf C doch genauso anwenden, oder?

von oskar aus der mülltonne (Gast)


Lesenswert?

Ich glaube soviel Auswahl gibt es da gar nicht. Doxygen, Natural Docs, 
.. ? Da gibt es allerdings auch keinen Support für ISRs und wie es mit 
Makros aussieht weiß ich auch nicht.

Doxygen gefällt mir persönlich nicht, rein visuell vom rohen Endprodukt 
her.

Vielleicht wäre das ein interessantes Projekt, einfach einen pseudo-AST 
mit z.B. python parsen und dann mit Genshi html oder xml ausgeben. Das 
ganze natürlich speziell auf C im Embedded Bereich zugeschnitten. Für 
Ada sieht es da glaube ich auch relativ lau aus.. wobei es hier 
natürlich die Spec Files gibt.

von Simon B. (nomis)


Lesenswert?

Natürlich alles hochsubjektiv, dennoch hier einige Sachen die mir 
wichtig sind:

- Whitespace großzügig eingesetzt hilft normalerweise.
   Insbesonders finde ich funktions_aufrufe (mit, spaces); schöner.

- Tabs sind verboten.
   Die Idee, dass sich jeder selber seinen persönlichen
   Indentation-level aussuchen kann, funktioniert in der
   Praxis nicht. Insbesonders wenn z.B. Funktionsaufrufe
   in mehrere Zeilen umbrochen werden. Ich sehe dann
   regelmäßig sowas:
1
<tab><tab>funktions_aufruf (argument1,
2
<tab><tab><tab><tab><tab>   argument2);
   und das bricht sofort, sobald die tab-Breite umgestellt wird.
1
<tab><tab>funktions_aufruf (argument1,
2
<tab><tab><space><space..>  argument2);
   So müsste es aussehen, damit es funktionieren soll.

- Zeilen möglichst auf 80 Zeichen Breite beschränken.

- Elemente untereinander ausrichten hilft, z.B. bei Funktionsprototypen:
1
static int
2
funktion_mit_vielen_argumenten (int      foobarbaz,
3
                                MyType  *blablablam,
4
                                double   brum);

Viele Grüße,
        Simon

von Vlad T. (vlad_tepesch)


Lesenswert?

Simon Budig schrieb:
> - Zeilen möglichst auf 80 Zeichen Breite beschränken.

finde ich eine absolute Sinnlosregel.
Die Zeiten von Kommandozeilen-Editoren im Textmodus sind vorbei.
bei 80 cols ist ein viertel der Editorzeile noch leer und das bei 
geöffnetem Projektbaum und vertikaler Taskkbar.
Zumal bei deskriptiven Variablen und Funktionsnamen dieses limit sehr 
schnell erschöpft ist.

Außerdem finde ich Kommentare hinter dem Code besser als dazwischen.
So kann man ungestört den Code lesen und wird nicht ständig duch 
abwechselnde Kommentare/Code gestört.

edit:
ansonsten stimme ich dir voll und ganz zu. (bis auf die Leerzeichen vor 
der öffnenden Klamme ;)

von Simon B. (nomis)


Lesenswert?

Vlad Tepesch schrieb:
> Simon Budig schrieb:
>> - Zeilen möglichst auf 80 Zeichen Breite beschränken.
>
> finde ich eine absolute Sinnlosregel.
> Die Zeiten von Kommandozeilen-Editoren im Textmodus sind vorbei.
> bei 80 cols ist ein viertel der Editorzeile noch leer und das bei
> geöffnetem Projektbaum und vertikaler Taskkbar.

Nunja, es kommt nicht nur von der Terminalbreite her.

Zunächst ist eine Faustregel aus der Typographie, dass eine Zeile in 
einem Textdokument nur 60-70 Zeichen enthalten soll, darüber leidet die 
Lesbarkeit. Nun ist das zugegebenermaßen auf Sourcecode nur begrenzt 
anwendbar, aber gibt zumindest einen Hinweis, dass man nicht endlos 
ausufern sollte, weil dann die Übersicht leidet.

Dann habe ich mal nach "eclipse screenshot" in der Bildersuche gegoogelt 
und mir mal einen der erstbesten Hits angeguckt ( 
http://www.jdave.org/images/jdave-eclipse-screenshot.png ). Da passen 
trotz 1600'er Auflösung gerade mal 90 Zeichen in eine Zeile. In einigen 
– anscheinend – real-world screenshots gucken die Leute (für mich 
unverständlich) nur noch durch ein Guckloch auf ihren Sourcecode.

Und nur sehr sehr wenige Leute haben irgendwie einen platzsparenden 
Spezial-Coder-Font in Verwendung, es gibt sogar einige, die 
proportionale Fonts verwenden (grusel).

Wenn man nicht nur für sich selber programmiert, halte ich 80 Zeichen 
nach wie vor für ein sinnvolles Maß.

> Zumal bei deskriptiven Variablen und Funktionsnamen dieses limit sehr
> schnell erschöpft ist.

Das stimmt natürlich. Deswegen gewinnen meiner Meinung nach die 
Konventionen für umbrochene Funktionsaufrufe an Bedeutung.

> Außerdem finde ich Kommentare hinter dem Code besser als dazwischen.
> So kann man ungestört den Code lesen und wird nicht ständig duch
> abwechselnde Kommentare/Code gestört.

Das stimmt, allerdings sollten längere Kommentarblöcke dann 
sinnvollerweise auch "in einer zweiten Spalte" getippt werden, das habe 
ich allerdings noch nicht in der real-world gesehen.

Viele Grüße,
        Simon

von Yalu X. (yalu) (Moderator)


Lesenswert?

Ein paar Dinge hat Simon schon vorweggenommen, trotzdem:

Vlad Tepesch schrieb:
> Simon Budig schrieb:
>> - Zeilen möglichst auf 80 Zeichen Breite beschränken.
>
> finde ich eine absolute Sinnlosregel.

So sinnlos finde ich diese Regel nicht.

> Die Zeiten von Kommandozeilen-Editoren im Textmodus sind vorbei.

Die Regel, dass eine Zeile nicht wesentlich länger als 80 Zeichen sein
sollte, stammt nicht aus der frühen Computertechnik und ihren
Restriktionen, sondern aus dem Buchdruck. Sie dient einfach dazu, dem
Auge beim zeilenweisen Lesen den Sprung vom Ende einer Ziele zu Anfang
der nächsten Zeile zu erleichtern. Deswegen werden großformatige
Publiklationen, wie bspw. Zeitungen, mehrspaltig gedruckt.

> bei 80 cols ist ein viertel der Editorzeile noch leer

Bei mir sind bei 80 Zeichen sogar fast noch 3/4 des Editorfensters leer,
trotzdem finde ich Programmzeilen mit 320 Zeichen nicht schön zu lesen.
Wenn eine Anweisung tatsächlich so lang wird, sollte man sich überlegen,
ob sie nicht zu kompliziert ist und allein schon deswegen besser in
mehrere übersichtliche Einzelstücke umgebrochen wird.

> Zumal bei deskriptiven Variablen und Funktionsnamen dieses limit sehr
> schnell erschöpft ist.

Deskriptiv heißt nicht geschwätzig. Wenn fast alle deiner Variablennamen
mehr als 10 Zeichen haben, machst du etwas falsch. Und von 10-buchstabi-
gen Variablen haben immerhin locker 6 Stück — einschließlich Einrückung,
Operatoren und Leerzeichen dazwischen — in einer 80-Zeichen-Zeile Platz.

Karl heinz Buchegger schrieb:
> Wenn du es deinem 'Nachleser' einfacher machen willst, dann stellst du
> deinen Editor so ein, dass er Tabulatoren durch Leerzeichen ersetzt.

Simon Budig schrieb:
> - Tabs sind verboten.

Vlad Tepesch schrieb im Beitrag #1780547 als Antwort:
> ansonsten stimme ich dir voll und ganz zu.

Ich finde es schön, dass hier doch einige sind, die diese vermaledeiten
Tabulatoren ablehnen. Dieses Relikt aus dem Fernschreiberzeitalter ist
leider nicht tot zu kriegen. Auch der Formfeed zur Trennung zwischen
einzelnen Unterprogramme u.ä. ist zum Glück weitgehend ausgestorben
(obwohl er im Programmcode sogar weniger gestört hat), warum schicken
wir den Tabulator nicht gleich hinterher?

von oskar aus der mülltonne (Gast)


Lesenswert?

Für die, die es interessiert, gibt es hier eine Zusammenstellung einiger 
Coding Fonts. In den Kommentaren finden sich auch noch weitere 
Empfehlungen.

http://www.codinghorror.com/blog/2007/10/revisiting-programming-fonts.html

80 Zeichen finde ich eine absolut sinnvolle Regel. Zum einen hat man 
dann keine Probleme, falls man dann doch mal am Terminal, SSH, telnet 
arbeiten muss, oder möchte - weil es evtl. 
schneller/besser/was-auch-immer ist -, was den Windows-Leuten hier 
wahrscheinlich nicht passieren wird.
Zum anderen was viel wichtiger ist, erkennt man dann, wenn eine Zeile zu 
lang ist.
Das hier:
1
uint8_t xyzBeliebigerBezeichner = Funktion1(AndereFunktion(NochMehr((cast)Variable))) * 5 + 3;

Finde ich schon arg Grenzwertig. Eine oder zwei Zeilen mehr zu benutzen 
erhöht hier die Lesbarkeit und kostet auch meistens nichts, weil der 
compiler das wegoptimiert.

von Peter D. (peda)


Lesenswert?

Vlad Tepesch schrieb:
> Die Zeiten von Kommandozeilen-Editoren im Textmodus sind vorbei.
> bei 80 cols ist ein viertel der Editorzeile noch leer und das bei
> geöffnetem Projektbaum und vertikaler Taskkbar.

Manchmal will man ja auch mal Programme ausdrucken, ohne Augenkrebs zu 
bekommen.
Und manchmal hat man noch mehrere Dokumente daneben offen, z.B. das 
Datenblatt.
Ich finde, daß man mit 80 Zeichen gut zurechtkommt.


Peter

von High Performer (Gast)


Lesenswert?

>Die Zeiten von Kommandozeilen-Editoren im Textmodus sind vorbei.

ACK. Ich verwende inzwischen 90 Zeichen. Dadurch lässt sich so mancher
Umbruch sparen.

>bei 80 cols ist ein viertel der Editorzeile noch leer und das bei
>geöffnetem Projektbaum und vertikaler Taskkbar.

Ihr wolltet ja unbedingt WideScreen, wo an Höhe gespart und in der 
Breite angebaut wird. Ich wollte das nicht ;-)

Im Ernst: Habe erst gestern einen längeren Brief, in dem ich mein 
Missfallen darin ausdrücke, dass es keine 4:3-Systeme mehr gibt, an etwa 
zehn Notebookhersteller geschickt. Auch hier auf mikrocontroller.net gab 
es ja bereits entsprechende Threads, und ich gehe deshalb davon aus, 
dass es nicht nur zwei Leute sind, die das ähnlich sehen.

>Zunächst ist eine Faustregel aus der Typographie, dass eine Zeile in
>einem Textdokument nur 60-70 Zeichen enthalten soll,

Programmtext hat jedoch mit Typographie zuerst mal gar nichts zu tun. Da 
gelten völlig andere Regeln, schon deshalb, weil Programmtext mit 
normalem Fließtext nicht zu vergleichen ist.

>darüber leidet die
>Lesbarkeit. Nun ist das zugegebenermaßen auf Sourcecode nur begrenzt
>anwendbar, aber gibt zumindest einen Hinweis, dass man nicht endlos
>ausufern sollte, weil dann die Übersicht leidet.

Ich bin der Meinung, dass ein Umbruch wesentlich schädlicher ist als 
eine lange Zeile. Ich denke, 90 Zeichen sind schon vertretbar, 100 
Zeichen vermutlich gerade noch so.


>Dann habe ich mal nach "eclipse screenshot" in der Bildersuche gegoogelt
>und mir mal einen der erstbesten Hits angeguckt (
>http://www.jdave.org/images/jdave-eclipse-screenshot.png ). Da passen
>trotz 1600'er Auflösung gerade mal 90 Zeichen in eine Zeile.

Wobei das mit der Auflösung zuerst mal gar nichts zu tun hat.

>In einigen
>– anscheinend – real-world screenshots gucken die Leute (für mich
>unverständlich) nur noch durch ein Guckloch auf ihren Sourcecode.

ACK! Auch für mich völlig unverständlich. Aber im Screenshot wird auch 
eine gigantisch große Schrift verwendet. Oben und unten halte ich so 
viel frei wie möglich. Horizontal habe ich selbst auf einem 4:3-System 
mit 90 Zeichen pro Zeile kein Problem.

von High Performer (Gast)


Lesenswert?

>Deskriptiv heißt nicht geschwätzig. Wenn fast alle deiner Variablennamen
>mehr als 10 Zeichen haben, machst du etwas falsch.

Nun ja: Name eines Objektes plus Name der Methode + als Argument wieder
ein Objektname plus ein Methodenname, da ist nicht mehr viel Luft bis zu 
den 80 Zeichen. Dann noch Einrückungen + Punkte + Klammern + Semikolon.
Ich verwende aussagekräftige Instanznamen, und sehe nicht ein, nur wegen 
des 80er-Dogmas hieroglyphen zu verwenden. Ich habe mit reichlich 
Programmen zu tun, die das so handhaben, und finde es frech, den anderen 
Lesern gegenüber.

Übrigens: SwingUtilities.invokeLater(...); Nur so als Beispiel, und es 
gibt noch längere...

oder mainWindow.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

sind bereits fast 60 Zeichen.

von High Performer (Gast)


Lesenswert?

>Manchmal will man ja auch mal Programme ausdrucken, ohne Augenkrebs zu
>bekommen.

Ich glaube, ich habe vor ca. 15 Jahren zum letzten Mal einen 
Programmtext gedruckt. Wozu auch?

von Kommste rein? Kiekste raus! (Gast)


Lesenswert?

Ein soeben gefundenes Snippet (eines der eher mäßig "langen"):

1
if( SHTxxSendCommand( SHTxx_MEASURE_RELATIVE_HUMIDITY_COMMAND ) != SHTxx_SEND_COMMAND_SUCCESSFUL )
2
{
3
   return( SHTxx_MEASURE_HUMIDITY_NOT_SUCCESSFUL_SEND_COMMAND_FAILED );
4
}

if-Abfrage: 99 Zeichen. Was soll daran unleserlich sein?

Yalu X. schrieb:
> Deskriptiv heißt nicht geschwätzig. Wenn fast alle deiner Variablennamen
> mehr als 10 Zeichen haben, machst du etwas falsch.

Streitbar. Lieber einen etwas längeren Variablen-/Funktionsnamen als 
nach einem Jahr Codeabstinenz wieder im Urschleim anzufangen.

Ansonsten: Klammern, Klammern, Klammern!

von Alexander S. (esko) Benutzerseite


Lesenswert?

Offtopic:
High Performer schrieb:
> Ihr wolltet ja unbedingt WideScreen, wo an Höhe gespart und in der
> Breite angebaut wird. Ich wollte das nicht ;-)

Ich auch nicht. Das ist eine unsinnige Entwicklung die unüberlegt von 
Filmen/DVDs für Monitore übernommen wurde.
Ich habe den Verdacht das dies aus Marketinggründen erfolgte. So hat ein 
21"-Monitor 5:4 dieselbe Fläche≈Kosten wie ein 22,5"-Monitor 16/9, 
klingt aber nach viel weniger. [1]

Noch schlimmer als die Verhältnismäßig kleine Fläche ist das ständige 
scrollen auf Websites oder DinA4 Dokumenten in Originalgröße.
Auf einen 19" 5:4 passt gerade noch eine A4 Seite.
Auf einem 23" 16:9 passt sie dagegen nicht mehr horizontal.


[1]
(21in)^2 * sin(arctan(5/4)) * cos(arctan(5/4)) =14dm²
(22,5in)^2 * sin(arctan(16/9)) * cos(arctan(16/9)) =14dm²

von Yalu X. (yalu) (Moderator)


Lesenswert?

Kommste rein? Kiekste raus! schrieb:
>> Deskriptiv heißt nicht geschwätzig. Wenn fast alle deiner Variablennamen
>> mehr als 10 Zeichen haben, machst du etwas falsch.
>
> Streitbar. Lieber einen etwas längeren Variablen-/Funktionsnamen als
> nach einem Jahr Codeabstinenz wieder im Urschleim anzufangen.

Aber gleich so einen?

> SHTxx_MEASURE_HUMIDITY_NOT_SUCCESSFUL_SEND_COMMAND_FAILED

Ich dachte erst, ich hätte zwei oder drei Operatoren zwischendrin
übersehen ;-)

von Andreas S. (andreas) (Admin) Benutzerseite


Lesenswert?

Ich halte auch nichts von der 80-Zeilen-Regel. Der Vergleich mit dem 
Buchdruck hinkt, denn Sourcecode liest man nicht wie Fließtext. I.d.R. 
liest man mit starker Gewichtung auf den Zeilenanfang: welche Variable 
wird zugewiesen, welche Funktion wird aufgerufen, was wird definiert. 
Der Rest der Zeile (wie wird der Zuweisungswert berechnet, was steht im 
7. Parameter des Funktionsaufrufs) interessiert erst sekundär.

von High Performer (Gast)


Lesenswert?

>Ich auch nicht.

Schön! Dann sind wir mindestens zu dritt.

>Das ist eine unsinnige Entwicklung die unüberlegt von
>Filmen/DVDs für Monitore übernommen wurde.

Unüberlegt sicher nicht. Der Durchschnittskunde ist unfähig oder nicht 
willens, rational zu entscheiden. Es wird gekauft, was stylisch oder 
modern aussieht. Nach der Brauchbarkeit wird nicht gefragt. Wichtig sind 
auch nur noch Zahlen: Zoll, Gigahertz, Terabyte. Kann dann schon mal 
jemand von seinem 3,1-Hertz-Computer schwärmt ;-)

Selbstverständlich sieht ein 16:9-Gerät neben einem 4:3-gerät aktuell 
stylischer aus, weil selbst das Prekariat sich inzwischen zwei, drei 
monströse Flachbildschirme im 16:9-Format leisten kann. Und was beim 
Fernseher gut ist, kann doch beim Computer nicht schlecht sein...

Mag sein, dass das Obige Geschreibsel arrogant oder menschenverachten 
klingt. Dennoch stehe ich zu meinen Aussagen. Ich kann doch nichts 
dafür, wenn viele Kunden im Laden das Gehirn abschalten.

Ich werde auch niemals nachvollziehen können, warum Männer damit 
prahlen, eine 300PS-Kiste zu fahren, die "bei 250 km/h abgeregelt ist".
Oder mit dem neuesten iPhone, iPad oder sonstwas. Immer wird geprahlt. 
Aber das ist wohl ein anderes Thema.

Und nein, ich bin kein Menschenfeind oder überproportional arrogant. Im 
Gegenteil.

>Ich habe den Verdacht das dies aus Marketinggründen erfolgte.

Ich auch! Schon wegen der kostengünstigen Möglichkeit, die Diagonale zu 
vergrößern.

Bei Gelegenheit, wenn alle Antworten eingetroffen sind oder nicht mehr 
mit weiteren Antworten zu rechnen ist, werde ich mal die Antworten der 
Hersteller sinngemäß hier posten. Es ist jedefalls schon jetzt, nach 
vier Antworten, höchst interessant, wie die Hersteller antworten.

von Kommste rein? Kiekste raus! (Gast)


Lesenswert?

Yalu X. schrieb:
> SHTxx_MEASURE_HUMIDITY_NOT_SUCCESSFUL_SEND_COMMAND_FAILED
>
> Ich dachte erst, ich hätte zwei oder drei Operatoren zwischendrin
> übersehen ;-)

Zugegeben, der ist einer der heftigen. :)  Aber der gehört zu einem 
Funktionsblock den man selten anguckt. Aber wenn man mal reinguckt 
(wenns mal nicht funktioniert) ist Klartext wie hier sehr nützlich zum 
debuggen.

von Rufus Τ. F. (rufus) Benutzerseite


Lesenswert?

High Performer schrieb:
> Ich glaube, ich habe vor ca. 15 Jahren zum letzten Mal einen
> Programmtext gedruckt. Wozu auch?

Damals, als ich noch auf einem Terminal mit 80x24-Auflösung gearbeitet 
habe, habe ich ziemlich viel auf unserem Schnelldrucker ausgedruckt, so 
etwa eine Kiste Papier pro Monat.

Seitdem ich mit anständigen Bildschirmauflösungen mehr Zeilen 
gleichzeitig sehen kann, ist der Bedarf dafür komplett entfallen.

Ich arbeite primär auf einem 4:3-Monitor mit 1600x1200 Pixeln Auflösung, 
der allerdings hochkant steht - was ca. 100 lesbare Sourcecodezeilen zur 
Folge hat. Ja, ich bin bekennender Consolas-mit-ClearType-Nutzer.

von Christian H. (netzwanze) Benutzerseite


Lesenswert?

Alexander Schmidt schrieb:
> Auf einem 23" 16:9 passt sie dagegen nicht mehr horizontal.

Ach, bei mir passen sogar locker zwei nebeneinander. Es ist sogar noch 
genügend Rand für Menüleiste, Schnellstartleiste, Taschenrechner, etc.

Ich bin über diese Monitore sehr glücklich, denn sie bieten mir viel 
Platz zum Arbeiten. Es ist für mich nicht erforderlich, dass eine 
A4-Seite auf volle Breite gezogen wird - noch brauche ich das nicht.

Ok, ich habe am Arbeitsplatz auch keinen Billigmonitor.

Peter Dannegger schrieb:
> Manchmal will man ja auch mal Programme ausdrucken, ohne Augenkrebs zu
> bekommen.
> Und manchmal hat man noch mehrere Dokumente daneben offen, z.B. das
> Datenblatt.
> Ich finde, daß man mit 80 Zeichen gut zurechtkommt.

Drucken geht noch gut mit 135 Zeichen die Zeile. Normalerweise reichen 
80 Zeichen aber aus. Nur selten ragen Kommentare über den Raus raus. Das 
aber auch nur, weil ich einen Kurzkommentar hinter den Code haben 
möchte.

High Performer schrieb:
> Ich glaube, ich habe vor ca. 15 Jahren zum letzten Mal einen
> Programmtext gedruckt. Wozu auch?

Ich drucke auch keine Programme mehr aus. Jedoch habe ich beruflich nur 
noch mit kürzeren Skripten zu tun, so das auch nicht mehr nötig ist.
Früher habe ich mir gerne mal die Programme ausgedruckt um sie mir in 
Ruhe anzusehen (auf den damaligen kleinen Röhrenmonitoren machte das 
keinen Spass).

Aber auch am modernen Monitor macht es keinen Spass, wenn man dauernd 
horizontal scrollen muss, um eine Codezeile zu betrachten. Ebenfalls 
öffne ich den Editor nicht im Vollbild, da ich ja noch andere Fenster 
sehen will.

90 Zeichen ist bei mir hier das äußerste Maximum. Mein Editor ist so 
eingestellt, dass er den Hauptbereich mit 80 Zeichen weiß darstellt. 
Alles was darüber hinaus geht, aber hellgrau. Auf diese Art passen ca 95 
Zeichen (habe es gerade nicht vor Augen) in das Fenster (von diesen habe 
ich öfters zwei nebeneinander auf). Durch die Farbabtrennung habe ich 
immer ein schlechtes Gewissen, wenn die Zeile in den grauen Bereich 
reicht.

von Alexander S. (esko) Benutzerseite


Lesenswert?

Christian H. schrieb:
>> Auf einem 23" 16:9 passt sie dagegen nicht mehr horizontal.
> Ach, bei mir passen sogar locker zwei nebeneinander.
Da ist mir ein Fehler unterlaufen, ich meinte vertikal.

von Simon B. (nomis)


Lesenswert?

High Performer schrieb:
> Bei Gelegenheit, wenn alle Antworten eingetroffen sind oder nicht mehr
> mit weiteren Antworten zu rechnen ist, werde ich mal die Antworten der
> Hersteller sinngemäß hier posten.

Würde mich prinzipiell interessieren, aber darf ich anregen, das in 
einem anderen Thread zu tun? Ist ja nicht so richtig direkt für dieses 
Thema relevant  :-)

Viele Grüße,
        Simon

von Jürgen (Gast)


Lesenswert?

Peter Dannegger (peda) wrote:
> Ich finde, daß man mit 80 Zeichen gut zurechtkommt.

Finde ich auch.

Irgendwo muß man die Grenze ziehen, und 80 Zeichen ist die einzige 
wirklich gebräuchliche Zeilenlänge, auf die man sich einigen könnte.

Argumente von Funktionen kann man übrigens umbrechen, wenn sie zu lang 
werden.

von High Performer (Gast)


Lesenswert?

>Ich bin über diese Monitore sehr glücklich, denn sie bieten mir viel
>Platz zum Arbeiten.

Die Bildschirmfläche hat jedoch zuerst einmal nichts mit dem 
Seitenverhältnis zu tun. Und wenn, dann ist es doch so, dass ein 20-Zoll 
4:3-Monitor eine deutlich größere Fläche hat als ein 20-Zoll 16:9-Gerät. 
Das ist doch einer der Gründe, warum es nur noch 16:9 gibt. Die 
Zollangabe bleibt gleich, aber dafür wird weniger Fläche benötigt. Gut 
für den Hersteller, schlecht für den Kunden. Im Übrigen bin ich der 
festen Überzeugung, und sehe das täglich auf Arbeitsplätzen 
verschiedenster Art, lässt sich vertikaler Platz besser nutzen als 
horizontaler.

von High Performer (Gast)


Lesenswert?

>Argumente von Funktionen kann man übrigens umbrechen, wenn sie zu lang
>werden.

Allerdings deutlich zu Lasten der Lesbarkeit. Zugunsten einer 
geringeren Anzahl von Umbrüchen packe ich lieber mehr Zeichen in eine 
Zeile. Wie gesagt, 90 halte ich durchaus noch für vertetbar. Früher 
waren bereits auf 640x480 Punkten 80 Zeichen üblich. Warum sollte man 
sich auch heute noch sklavisch daran halten. Es gibt einfach keinen 
Grund mehr dafür.

von Simon B. (nomis)


Lesenswert?

Nunja, solange wir uns grundsätzlich darüber einig sind, dass Zeilen 
nicht endlos lange werden sollten bin ich ja schon glücklich - ob nun 80 
oder 90 Zeichen – darüber will ich mich nicht streiten.

Allerdings bin ich der festen Überzeugung, dass Umbrüche der Lesbarkeit 
dienen können. Erstmal der Griff in mein Gruselkabinett: Aus den 
OpenGL-headerfiles:
1
typedef void (APIENTRYP PFNGLCOMPRESSEDTEXIMAGE3DPROC) (GLenum target, GLint level, GLenum internalformat, GLsizei width, GLsizei height, GLsizei depth, GLint border, GLsizei imageSize, const GLvoid *data);

mehr als 200 Zeichen. Keine weiteren Fragen euer Ehren. Und
fragt mich nicht was diese Großbuchstabenansammlung da soll. Letzteres 
mal außen vor gelassen und umformatiert:
1
typedef void (APIENTRYP PFNGLCOMPRESSEDTEXIMAGE3DPROC)
2
                  (GLenum         target,
3
                   GLint          level,
4
                   GLenum         internalformat,
5
                   GLsizei        width,
6
                   GLsizei        height,
7
                   GLsizei        depth,
8
                   GLint          border,
9
                   GLsizei        imageSize,
10
                   const GLvoid  *data);

(zur Verteidigung der GL-Sachen muss ich allerdings sagen, dass der Rest 
der Headerfiles deutlich brauchbarer aussieht).

Und in die umgekehrte Richtung hier etwas aus dem Gimp-Sourcecode. 
Erstmal die "ordentliche" Version aus dem originalen GIMP sourcecode:
1
void            gimp_layer_flatten             (GimpLayer            *layer,
2
                                                GimpContext          *context);
3
4
void            gimp_layer_resize_to_image     (GimpLayer            *layer,
5
                                                GimpContext          *context);
6
BoundSeg      * gimp_layer_boundary            (GimpLayer            *layer,
7
                                                gint                 *num_segs);
8
9
GimpDrawable * gimp_layer_get_floating_sel_drawable (const GimpLayer *layer);

(siehe auch das ganze Headerfile: 
http://git.gnome.org/browse/gimp/tree/app/core/gimplayer.h )

Jetzt mal den Ausschnitt ohne Ausrichtung und Zeilenumbrüche:
1
void gimp_layer_flatten (GimpLayer *layer, GimpContext *context);
2
void gimp_layer_resize_to_image (GimpLayer *layer, GimpContext *context);
3
BoundSeg * gimp_layer_boundary (GimpLayer *layer, gint *num_segs);
4
GimpDrawable * gimp_layer_get_floating_sel_drawable (const GimpLayer *layer);

Man sieht an diesem kleinen Beispiel (wir stoßen auch noch nicht mal 
ernsthaft an die 80 Zeichen), dass Umbrüche sehr wohl deutlich der 
Lesbarkeit dienen können. Wenn man sich den Luxus gönnt und ordentlich 
ausrichtet und evtl. wirklich konsequent die Argumente auf mehrere 
Zeilen verteilt, wird es plötzlich deutlich übersichtlicher. In meinem 
letzten Beispiel muss man ja schon anfangen zu suchen, nur um die 
Funktionsnamen als solche erkennen zu können.

Viele Grüße,
        Simon

von byte (Gast)


Lesenswert?

High Performer schrieb:
>>Manchmal will man ja auch mal Programme ausdrucken, ohne Augenkrebs zu
>>bekommen.
> Ich glaube, ich habe vor ca. 15 Jahren zum letzten Mal einen
> Programmtext gedruckt. Wozu auch?

Also ich druck immer noch / wieder. Keine Ahnung warum, aber auf dem 
Papier sehe ich immer Dinge, die mir auf dem Bildschirm nicht auffallen. 
Ausserdem "denke" ich gern auf Papier mit Bleistift. Somanch geniale 
Idee/Abkürzung ist auf dem Papier entstanden.

oskar aus der mülltonne schrieb:
> Doxygen gefällt mir persönlich nicht, rein visuell vom rohen Endprodukt
> her.

Mir auch nicht. Und ich versteh nicht warum sich jemand soviel Mühe für 
so ein Programm macht, und dann so hässliche/unübersichtliche Docs 
generiert. Der Documentor geht noch einigermaßen, da kann man auch die 
Templates anpassen. Aber is halt eigentlich für PHP.

von Vlad T. (vlad_tepesch)


Lesenswert?

byte schrieb:
> Mir auch nicht. Und ich versteh nicht warum sich jemand soviel Mühe für
> so ein Programm macht, und dann so hässliche/unübersichtliche Docs
> generiert. Der Documentor geht noch einigermaßen, da kann man auch die
> Templates anpassen. Aber is halt eigentlich für PHP.

du kannst bei doxygen auch so ziemlich alles anpassen, templates, 
footer, header, reihenfolge der Elemente, Stylesheets.

von oskar aus der mülltonne (Gast)


Lesenswert?

Vlad Tepesch schrieb:
> byte schrieb:
>> Mir auch nicht. Und ich versteh nicht warum sich jemand soviel Mühe für
>> so ein Programm macht, und dann so hässliche/unübersichtliche Docs
>> generiert. Der Documentor geht noch einigermaßen, da kann man auch die
>> Templates anpassen. Aber is halt eigentlich für PHP.
>
> du kannst bei doxygen auch so ziemlich alles anpassen, templates,
> footer, header, reihenfolge der Elemente, Stylesheets.

Das stimmt natürlich, aber die Rede war ja vom "rohen" Endprodukt. Und 
mir geht es so, dass wenn ich so ein Tool benutze, dann möchte ich auch 
ohne noch groß dran rumwerkeln ein halbwegs ordentliches Ergebnis haben.
Als Positiv-Beispiel möchte ich hier mal Sphinx nennen, das zwar eher 
nicht dazu geeignet ist Kommentare aus dem Quellcode zu parsen, aber ich 
finde das sieht, so wie es daher kommt, durchaus ansprechend aus. 
http://docs.python.org/library/bisect.html

von Mark B. (markbrandis)


Lesenswert?

Yalu X. schrieb:
> Deskriptiv heißt nicht geschwätzig. Wenn fast alle deiner Variablennamen
> mehr als 10 Zeichen haben, machst du etwas falsch.

Du hast anscheinend noch an keinem Projekt gearbeitet, in dem mehrere 
tausend (teilweise über zehntausend) Signalnamen bzw. Variablen 
vorkommen. Wenn man da noch einigermaßen den Überblick behalten will, 
muss man zwangsläufig längere Bezeichner verwenden. Die sehen dann zum 
Beispiel so aus:

<Sender>_<Art des Signals>_<Empfänger>_<wofür ist das Signal gut>

z.B.
ZSG_M_EVM_Status
CI_MN2_SBV1_betaetigt_FR1
CI_M1_HB_Druck_vorhanden
F_IO_M_LSS_Filterstrom_ein

Da mit 10 Zeichen auszukommen - na dann viel Spaß! ;-)

von oskar aus der mülltonne (Gast)


Lesenswert?

Vielleicht kann man sich darauf einigen, dass die Zahl der Buchstaben im 
Variablennamen ungefähr umgekehrt proportional zur Häufigkeit im 
Quelltext sein sollte?

von Karl H. (kbuchegg)


Lesenswert?

oskar aus der mülltonne schrieb:
> Vielleicht kann man sich darauf einigen, dass die Zahl der Buchstaben im
> Variablennamen ungefähr umgekehrt proportional zur Häufigkeit im
> Quelltext sein sollte?

Die übliche Empfehlung ist es, den Scope zu Hilfe zu nehmen.

Variablen mit einem kleinen Scope, können kurze Namen haben. Das 
klassische Beispiel ist das berühmte i in einer for-Schleife.

Variablen bzw. Konstante die systemweit benutzt werden können schon auch 
längere Namen besitzen, wobei es sich auch lohnt sich nach einer 
Nomenklatur umzusehen um die Namen nicht allzugroß werden zu lassen.

Gute Namen zu finden, egal ob für Variablen oder Funktionen, ist eine 
Wissenschaft für sich. Auf der einen Seite soll der Name etwas aussagen, 
auf der anderen Seite soll er aber auch nicht in eine Zeichenschlacht 
ausarten. Auf der einen Seite soll er einem Schema folgen, auf der 
anderen Seite sollen sich 2 beliebige Namen nicht erst im 15. Buchstaben 
unterscheiden. Ist er zu kurz, ist es nichts; ist er zu lang dann 
ermüdet man sehr schnell beim Lesen.

von Arne (Gast)


Lesenswert?

oskar aus der mülltonne schrieb:
> Gibt es sowas wie universelle Coding Conventions oder Richtlinien im
> µC-Bereich.

Google doch mal nach "indian hill" "style guide". Da findest Du sicher 
einiges zu.

von oskar aus der mülltonne (Gast)


Lesenswert?

Arne schrieb:
> Google doch mal nach "indian hill" "style guide". Da findest Du sicher
> einiges zu.

> Revision: 6.0 / 25 June 1990

Wo hast du denn dieses Fossil ausgegraben?

5. #define void or #define void int for compilers without the void 
keyword.
1
  c = (a == b)
2
    ? d + f(a)
3
    : f(b) - d;

schick!

von Yalu X. (yalu) (Moderator)


Lesenswert?

Hier ist ein neuerer C++-Style-Guide, der sich zu 95% mit meinem eigenen
Geschmack deckt, obwohl er vom bösen Onkel Google ;-) kommt:

  http://google-styleguide.googlecode.com/svn/trunk/cppguide.xml

Auch die restlichen 5% sind nicht wirklich gegen meinen Geschmack, so
dass ich mir gerade überlege, mich in zukünftigen Projekten vollständig
an diesen Guide zu halten, sofern nicht andere Randbedingungen höhere
dagegensprechen.

Der Google-Guide ist ziemlich umfassend und gibt nicht nur Regeln vor,
sondern bergündet diese auch. Als Bonbon gibt es ein Tool (cpplint), das
den Quellcode nach Regelverstößen untersucht.

Auch der Python-Style-Guide aus dem gleichen Hause ist nicht schlecht:

  http://google-styleguide.googlecode.com/svn/trunk/pyguide.html

von oskar aus der mülltonne (Gast)


Lesenswert?

Vielleicht hängt das damit zusammen, das Guido van Rossum bei Google 
ist.
Allerdings würde ich bei Python doch eher zu PEP 8 raten.

http://www.python.org/dev/peps/pep-0008/

bei den C++ Regeln geht mir doch schon einiges gegen den Strich.
1. finde ich .cpp besser als .cc (ok, geschmackssache)
2. We do not use C++ exceptions. <- WTF? nur die Exceptions der 
Standardlib + STL nicht oder das komplette Exception Handling nicht?
3. Use streams only for logging. <- was ist an Filestreams usw. falsch?
4. We do not allow default function parameters, except in a few uncommon 
situations explained below. <- default parameter halte ich für überaus 
sinnvoll, vor allem, wenn man kein overloading haben möchte.
5. Use a k followed by mixed case: kDaysInAWeek. <- auf Ungarische 
Notation verzichten und dann sowas, was soll das? Der compiler wirft zur 
Compile-time sowieso einen Fehler aus, wenn const in der deklaration 
steht.

von Yalu X. (yalu) (Moderator)


Lesenswert?

oskar aus der mülltonne schrieb:
> bei den C++ Regeln geht mir doch schon einiges gegen den Strich.
> 1. finde ich .cpp besser als .cc (ok, geschmackssache)
> 2. We do not use C++ exceptions. <- WTF? nur die Exceptions der
> Standardlib + STL nicht oder das komplette Exception Handling nicht?
> 3. Use streams only for logging. <- was ist an Filestreams usw. falsch?
> 4. We do not allow default function parameters, except in a few uncommon
> situations explained below. <- default parameter halte ich für überaus
> sinnvoll, vor allem, wenn man kein overloading haben möchte.
> 5. Use a k followed by mixed case: kDaysInAWeek.

Alle deine Punkte außer 3 gehören auch bei mir zu den 5%, die ich nicht
toll finde, mich aber notfalls im Sinne der allgemeinen Völkerverständi-
gung damit abfinden könnte.

Zu Punkt 3: Ich hätte nicht gedacht, dass es irgendjemanden auf der Welt
gibt, der in diesem Punkt mit mir einer Meinung ist, nachdem das Printf
in C++ von einigen selbsternannten Programmiergurus mittlerweile fast
mehr gesteinigt wird als das Goto.

Ich sehe ein, dass die printf-Funktion mit ihrer variablen Anzahl von
Argumenten und der mangelhaften Typprüfung (zumindest bei älteren
Compilern) nicht das Gelbe vom Ei ist, dafür ist die Anweisung knackig
kurz und man sieht gleich im ersten Argument (dem Formatstring), wie die
Ausgabe aussehen wird.

Die Stream-Notation in C++ hat zwar die genannten Nachteile nicht, dafür
ist sie mit großem Abstand das Aufgeblasenste und Unleserlichste, was
ich jemals in einer Programmiersprache (vielleicht mit Ausnahme von
Malbolge) gesehen habe, einfach völlig irre.

Das Ganze wurde noch verschärft durch die Einführung des std-Namespace.
Ohne "using namespace std" ist man praktisch komplett verloren.

von Vlad T. (vlad_tepesch)


Lesenswert?

Yalu X. schrieb:
> dafür
> ist sie mit großem Abstand das Aufgeblasenste und Unleserlichste, was
> ich jemals in einer Programmiersprache (vielleicht mit Ausnahme von
> Malbolge) gesehen habe, einfach völlig irre.

den jenigen, der sich die Shift-Operator-Überladung dafür ausgedacht hat 
hab ich auch schon des öfteren verflucht

von Rolf Magnus (Gast)


Lesenswert?

Mark Brandis schrieb:
> Yalu X. schrieb:
>> Deskriptiv heißt nicht geschwätzig. Wenn fast alle deiner
>> Variablennamen mehr als 10 Zeichen haben, machst du etwas falsch.
>
> Du hast anscheinend noch an keinem Projekt gearbeitet, in dem mehrere
> tausend (teilweise über zehntausend) Signalnamen bzw. Variablen
> vorkommen. Wenn man da noch einigermaßen den Überblick behalten will,
> muss man zwangsläufig längere Bezeichner verwenden.

Kann es sein, daß du nicht von normalen Variablen sprichst, sondern von 
autogeneriertem Code, wo's halt nicht anders geht?
Ansonsten würde ich nämlich dringend davon abraten, "flach" 10.000 
globale Variablen komplett ohne weitere Strukturierung zu definieren.

von D. I. (Gast)


Lesenswert?

Es wäre schön wenn das TAB tot wäre, allerdings steht mein Editor auch 
noch auf TAB, da man sonst unmöglich Makefiles schreiben kann (nur mal 
als Beispiel)

von oskar aus der mülltonne (Gast)


Lesenswert?

D. I. schrieb:
> Zu Punkt 3: Ich hätte nicht gedacht, dass es irgendjemanden auf der Welt
> gibt, der in diesem Punkt mit mir einer Meinung ist, nachdem das Printf
> in C++ von einigen selbsternannten Programmiergurus mittlerweile fast
> mehr gesteinigt wird als das Goto.

Goto kann in Exremfällen doch zur lesbarkeit beitragen und "mag" dann 
berechtigt sein, aber meistens kommt man doch ohne aus und sollte das 
auch tun. Aber wie gesagt in den 0,1% der Fälle macht es vielleicht doch 
Sinn.

Printf in C++ ist mMn völlig in Ordnung. Und wenn man printf + streams 
verwenden will, dann leitet man stdout halt um. Ich finde beides nicht 
kompliziert oder schwer verständlich.

D. I. schrieb:
> den jenigen, der sich die Shift-Operator-Überladung dafür ausgedacht hat
> hab ich auch schon des öfteren verflucht

beim Operator-Overloading muss man doch sowieso extrem vorsichtig sein. 
Wobei sowas wie ein Vektor-Typ auch nicht ohne implementiert werden 
kann. Shift-Operator-overloading auch zuzulassen ist nur konsequent. 
Allerdings sollte jeder Programmierer doch aufpassen, was er macht. Und 
Vielleicht gibt es doch einige Fälle in denen es sind macht den Shift 
operator zu überladen.

Rolf Magnus schrieb:
> Ansonsten würde ich nämlich dringend davon abraten, "flach" 10.000
> globale Variablen komplett ohne weitere Strukturierung zu definieren.

Was schlägst du denn vor? structs zu definieren?
namespaces gibt es in C99 nämlich nicht.

von oskar aus der mülltonne (Gast)


Lesenswert?

Ich möchte nochmal kurz was zum Goto zitieren:


"Ein Goto hat wenige Anwendungen in allgemeiner 
High-level-Programmierung, aber es kann sehr hilfreich sein, wenn 
C++-Code von einem Programm generiert und nicht von einer Person 
geschreiben wird; beispielsweise können gotos in einem Parser benutzt 
werden, der aus einer Grammatik von einem Parsergenerator erzeugt wurde. 
Das goto kann auch in den seltenen Fällen wichtig sein, in denen 
optimale Effizienz absolut notwendig ist, z.B. in der inneren Schleife 
einer Echtzeitanwendung.
Eine der wenigen sinnvollen Anwendungen von goto in normalem Code ist 
der Ausstieg aus einer verschachtelten Schleife oder switch-Anweisung 
(ein break verlässt nur die nächste umscließende Schleife oder 
switch-Anweisung)."
1
for (int i = 0; i < 10; ++i)
2
    for(int j = 0; j < 10; ++j)
3
        if (array[i][j]) goto gefunden;
4
5
gefunden:
6
    //xy

Ich muss sagen das obere Beispiel gefällt mir wirklich besser als z.B.
1
bool break_flag = false;
2
for (int i = 0; i < 10; ++i) {
3
    if (break_flag)
4
        break;
5
6
    for(int j = 0; j < 10; ++j)
7
        if (array[i][j]) {
8
            break_flag = true;
9
            break;
10
        }
11
}

von oskar aus der mülltonne (Gast)


Lesenswert?

Das Ergebnis von diesem Parser möchte ich allerdings nicht debuggen! 
Sonst kann man auch gleich alles in asm machen.

von Mark B. (markbrandis)


Lesenswert?

Rolf Magnus schrieb:
> Kann es sein, daß du nicht von normalen Variablen sprichst, sondern von
> autogeneriertem Code, wo's halt nicht anders geht?
> Ansonsten würde ich nämlich dringend davon abraten, "flach" 10.000
> globale Variablen komplett ohne weitere Strukturierung zu definieren.

Im Prinzip ja, die Variablen entstammen einer 
Schnittstellenspezifikation für den Feldbus und werden aus einem Excel 
(Bäh) File heraus "generiert". Ob man die Signalnamen nun aber im Code 
oder im Excel-File auseinanderhalten muss, ist egal - im Endeffekt muss 
man beides.

von oskar aus der mülltonne (Gast)


Lesenswert?

Mark Brandis schrieb:
> Im Prinzip ja, die Variablen entstammen einer
> Schnittstellenspezifikation für den Feldbus und werden aus einem Excel
> (Bäh) File heraus "generiert".

dann wäre es doch bestimmt kein Problem die Signalnamen noch nebenbei in 
namespaces zu verpacken oder?
das würde die ganz Sache sicher übersichtlicher machen.

von cee (Gast)


Lesenswert?

oskar aus der mülltonne schrieb:
> for (int i = 0; i < 10; ++i)
> ...
> bool break_flag = false;
> ...

Sorry, aber das is beides Murx.

von Vlad T. (vlad_tepesch)


Lesenswert?

oskar aus der mülltonne schrieb:
> dann wäre es doch bestimmt kein Problem die Signalnamen noch nebenbei in
> namespaces zu verpacken oder?
> das würde die ganz Sache sicher übersichtlicher machen.

1. wie erstellt man denn in C Namespaces?
2. durch Namespaces werden die Namen auch nicht kürzer.
   Statt einem _ kommt dann halt ein ::

von Tim T. (tim_taylor) Benutzerseite


Lesenswert?

Und was spricht dagegen diese Suche in eine Funktion zu packen, die du 
dann einfach mit einem return verlassen kannst?
1
bool suche( void ) {
2
 int i, j;
3
4
 for ( i = 0; i < 10; ++i ) 
5
  for ( j = 0; j < 10; ++j )
6
   if ( array[i][j] ) return true;
7
8
 return false;
9
}

von Vlad T. (vlad_tepesch)


Lesenswert?

Tim T. schrieb:
> Und was spricht dagegen diese Suche in eine Funktion zu packen, die du
> dann einfach mit einem return verlassen kannst?

das pro Funktion nur ein return-Statement erlaubt ist.

von Tim T. (tim_taylor) Benutzerseite


Lesenswert?

Vlad Tepesch schrieb:
> Tim T. schrieb:
>> Und was spricht dagegen diese Suche in eine Funktion zu packen, die du
>> dann einfach mit einem return verlassen kannst?
>
> das pro Funktion nur ein return-Statement erlaubt ist.

Und das ist irgendwie totaler Schwachfug...

von Mark B. (markbrandis)


Lesenswert?

oskar aus der mülltonne schrieb:
> dann wäre es doch bestimmt kein Problem die Signalnamen noch nebenbei in
> namespaces zu verpacken oder?

Doch, wenn man eine Programmiersprache verwendet die keine Namensräume 
kennt... :-)

von Yalu X. (yalu) (Moderator)


Lesenswert?

Tim T. schrieb:
>>> Und was spricht dagegen diese Suche in eine Funktion zu packen, die du
>>> dann einfach mit einem return verlassen kannst?
>>
>> das pro Funktion nur ein return-Statement erlaubt ist.
>
> Und das ist irgendwie totaler Schwachfug...

Naja, ein Return mitten in einer verschachtelten  Schleife unterscheidet
sich ja nicht arg von einem Goto ans Funktionsende.

Vorteil vom Return: Man sieht sofort, dass an dieser Stelle die Funktion
verlassen wird, während man beim Goto — insbesondere bei wenig aussage-
kräftigem Label-Namen — erst nachschauen muss, wohin der Sprung führt.

Vorteil vom Goto: Stellt sich sofort oder später heraus, dass am
Funktionsende noch irgendwelche Aufräumaktionen durchgeführt werden
müssen, braucht man diese nur hinter das Goto-Label zu schreiben. Bei
der Returnvariante muss man den Aufräumcode duplizieren, da es zwei
Funktionsausgänge gibt. Duplizierter Code ist aber meistens schlecht.

Ein Goto mit einem aussagekräftigen Label-Namen würde ich deswegen einem
Mehrfach-Return vorziehen. Da der Goto nach MISRA und vielen anderen
Programmierrichtlinien aber verboten ist, muss es meiner Meinung nach
der Mehrfach-Return erst recht sein.

von Rolf Magnus (Gast)


Lesenswert?

D. I. schrieb:
> Es wäre schön wenn das TAB tot wäre, allerdings steht mein Editor auch
> noch auf TAB, da man sonst unmöglich Makefiles schreiben kann (nur mal
> als Beispiel)

Erkennt der denn nicht, daß es ein Makefile ist und da Tabs auf jeden 
Fall benötigt werden?

oskar aus der mülltonne schrieb:
> D. I. schrieb:
>> den jenigen, der sich die Shift-Operator-Überladung dafür ausgedacht
>> hat hab ich auch schon des öfteren verflucht
>
> beim Operator-Overloading muss man doch sowieso extrem vorsichtig sein.
> Wobei sowas wie ein Vektor-Typ auch nicht ohne implementiert werden
> kann. Shift-Operator-overloading auch zuzulassen ist nur konsequent.

Es geht glaube ich nicht um die Möglichkeit der Überladung von 
Shift-Operatorn, sondern darum, daß diese für Stream-Ein-/Ausgabe 
mißbraucht wurden.

> Allerdings sollte jeder Programmierer doch aufpassen, was er macht.

Bei Operator-Überladung wird viel Schindluder getrieben. Wenn ich mir 
boost so anschaue ... da wimmelt es davon geradezu, z.B. in 
boost::format, das den Modulo-Operator als Stream-Operator mißbraucht.
Gekrönt wird es aber von boost::spirit, das C++ komplett verbiegt, indem 
es so ziemlich alle Operatoren überlädt, damit sich an der Stelle C++ so 
verhält, als sei es eine komplett andere Sprache (EBNF in dem Fall).

> Rolf Magnus schrieb:
>> Ansonsten würde ich nämlich dringend davon abraten, "flach" 10.000
>> globale Variablen komplett ohne weitere Strukturierung zu definieren.
>
> Was schlägst du denn vor? structs zu definieren?

Ja.

oskar aus der mülltonne schrieb:
> Das goto kann auch in den seltenen Fällen wichtig sein, in denen
> optimale Effizienz absolut notwendig ist, z.B. in der inneren Schleife
> einer Echtzeitanwendung.
> Eine der wenigen sinnvollen Anwendungen von goto in normalem Code ist
> der Ausstieg aus einer verschachtelten Schleife oder switch-Anweisung
> (ein break verlässt nur die nächste umscließende Schleife oder
> switch-Anweisung)."

Das finde ich nicht nur für die Effizienz, sondern auch für die 
Lesbarkeit vorteilhaft, wie dein Beispiel ja auch zeigt.
Und an Stellen, wo es die Lesbarkeit verbessert, goto nicht einzusetzen, 
nur weil "goto böse ist", ist einfach nur dumm, denn die Abneigung gegen 
goto kommt ja ursprünglich daher, daß es die Lesbarkeit oft 
verschlechtert.

cee schrieb:
> oskar aus der mülltonne schrieb:
>> for (int i = 0; i < 10; ++i)
>> ...
>> bool break_flag = false;
>> ...
>
> Sorry, aber das is beides Murx.

Was soll daran "Murx" sein?

oskar aus der mülltonne schrieb:
> Mark Brandis schrieb:
>> Im Prinzip ja, die Variablen entstammen einer
>> Schnittstellenspezifikation für den Feldbus und werden aus einem Excel
>> (Bäh) File heraus "generiert".
>
> dann wäre es doch bestimmt kein Problem die Signalnamen noch nebenbei
> in namespaces zu verpacken oder?

Wenn in dem Excel-File keine Struktur drin ist, kann man auch keine 
herzaubern. Es müßte sich jemand hinsetzen und jedes Signal einzeln von 
Hand einer Gruppe zuordnen und diese benennen. Außerdem müßte man die 
Signale dann ja alle umbenennen, damit die Namen überhaupt kürzer 
werden. Und wenn dann nachher im Code die Namen anders sind, als z.B. im 
Analysetool, ist das auch blöd.

von oskar aus der mülltonne (Gast)


Lesenswert?

Mark Brandis schrieb:
> Doch, wenn man eine Programmiersprache verwendet die keine Namensräume
> kennt... :-)

Dann ist das natürlich keine Möglichkeit ;), ich war von C++ 
ausgegangen..


Rolf Magnus schrieb:
> 2. durch Namespaces werden die Namen auch nicht kürzer.
>    Statt einem _ kommt dann halt ein ::

der einfache Vorteil liegt doch dadrin, dass der lokale Scope nicht 
vollgestopft ist. Das ermöglicht zum Beispiel eine bequemere Code 
Completion, weil nicht 10k Signale in der 
Code-Completion-Drop-Down-Liste angezeigt werden, sondern nur die, die 
man eben grade benutzen möchte.
Jeder Signalname wird dann um - sagen wir mal - seinen Sender kürzer, 
denn den kann man in das Modul mit
1
using namespace <Sender>
 einbinden, denn jedes Modul verwendet sicher nicht jedes Signal.

Rolf Magnus schrieb:
> Wenn in dem Excel-File keine Struktur drin ist, kann man auch keine
> herzaubern. Es müßte sich jemand hinsetzen und jedes Signal einzeln von
> Hand einer Gruppe zuordnen und diese benennen. Außerdem müßte man die
> Signale dann ja alle umbenennen, damit die Namen überhaupt kürzer
> werden. Und wenn dann nachher im Code die Namen anders sind, als z.B. im
> Analysetool, ist das auch blöd.

Man könnte, wenn das Signal zum Beispiel so aussieht:

<SIGNALTYP>_<SENDER>_<EMPFÄNGER>

am ersten Unterstrich den Signalnamen auftrennen. Das vorne wird der 
namespace, das dahinter der Bezeichner für das konkrete Signal.

Nur ein Beispiel, ich habe keine Ahnung, wie das alles konkret aussieht.

Mark Brandis schrieb:
> Doch, wenn man eine Programmiersprache verwendet die keine Namensräume
> kennt... :-)

Rolf Magnus schrieb:
>> Was schlägst du denn vor? structs zu definieren?
>
> Ja.


Das ist glaube ich die übliche Variante. Allerdings natürlich 
Zweckentfremdung..



Tim T. schrieb:
> Und was spricht dagegen diese Suche in eine Funktion zu packen, die du
> dann einfach mit einem return verlassen kannst?

eine Sache die dagegen spricht ist, das du in der Funktion eventuell 
noch mit dem Array und i und j arbeiten möchtest.

Die Funktion könnte meinetwegen die Aufgabe "finde den ersten schwarzen 
Pixel und färbe in grün" haben.
Die Funktion durchsucht das 2D Array nach dem ersten Treffer. Eine 
Funktion kann maximal einen Wert zurückgeben. Also müsste man sich 
zusätzlich einen Typ (struct) definieren, der aus zwei ints besteht, x- 
und y-koordinate. Den Typ müsste man dan zurückgeben an eine Funktion, 
die dann den gefunden Pixel grün färbt.

Das ist deutlich mehr Aufwand, als wenn man ein klares goto verwendet.
Das Label muss ja nichteinmal am Funktionsende stehen, sondern kann 
direkt auf die verschachtelte For-Schleife folgen, dann gibt es ganz 
sicher keine Probleme mit dem Verständnis.

Yalu X. schrieb:
> Ein Goto mit einem aussagekräftigen Label-Namen würde ich deswegen einem
> Mehrfach-Return vorziehen. Da der Goto nach MISRA und vielen anderen
> Programmierrichtlinien aber verboten ist, muss es meiner Meinung nach
> der Mehrfach-Return erst recht sein.

Das ist auch wieder eine sinnlose Vorschrift. Viel eher sollte dem 
Programmierer angeraten werden, Goto oder mehrfach-return nur zu 
verwenden, wenn es an der betreffenden Stelle einen nutzen gibt, der die 
Nachteile - also in der Regel unleserlichkeit - überwiegt.

Hier sind noch ein paar Beispiele für die Sinnvolle Nutzung von goto:

http://kerneltrap.org/node/553/2131

von Vlad T. (vlad_tepesch)


Lesenswert?

@oskar:
bitte immer in dem Beitrag auf "Markierten Text zitieren klicken", indem 
du auch was selektiert hast. ansonsten stimmt der Name und der Link 
nicht.

Tim T. schrieb:
>> das pro Funktion nur ein return-Statement erlaubt ist.
>
> Und das ist irgendwie totaler Schwachfug...

das stimm, das habe ich weiter oben auch schon erwähnt.
Trotztdem wird es von MISRA so vorgschrieben.

oskar aus der mülltonne schrieb:
> der einfache Vorteil liegt doch dadrin, dass der lokale Scope nicht
> vollgestopft ist. Das ermöglicht zum Beispiel eine bequemere Code
> Completion, weil nicht 10k Signale in der
> Code-Completion-Drop-Down-Liste angezeigt werden

das ist mir durchaus bewusst.
die gibts trotzdem nur in c++

von oskar aus der mülltonne (Gast)


Lesenswert?

Vlad Tepesch schrieb:
> @oskar:
> bitte immer in dem Beitrag auf "Markierten Text zitieren klicken", indem
> du auch was selektiert hast. ansonsten stimmt der Name und der Link
> nicht.

Oh, das tut mir Leid, das habe ich nicht gemerkt, ich dachte, das 
passiert automatisch.

Vlad Tepesch schrieb:
> das ist mir durchaus bewusst.
> die gibts trotzdem nur in c++

Das stimmt natürlich.
Wie gesagt, bin ich von c++ ausgegangen.. Die vermurkste Alternative 
wären halt structs.

Oder gleich Ada ;). Ich finde Ada sollte mehr Unterstützung/Verbreitung 
finden, vor allem im Anfänger-Bereich, weil man hier erstmal lernt 
einigermaßen aufgeräumt zu Programmieren (z.B. 
Deklarations-/Anweisungs-Teil, ordentliche Deklaration der Parameter mit 
In/Out...) und trotzdem viele fortgeschrittene Sprachmittel - Generics 
z.B. - hat...

von Karl H. (kbuchegg)


Lesenswert?

Vlad Tepesch schrieb:

> Tim T. schrieb:
>>> das pro Funktion nur ein return-Statement erlaubt ist.
>>
>> Und das ist irgendwie totaler Schwachfug...
>
> das stimm, das habe ich weiter oben auch schon erwähnt.
> Trotztdem wird es von MISRA so vorgschrieben.

Wie so viele Regeln ist auch das eine Regel, die im Allgemeinen nicht 
schlecht ist, im Speziellen aber Unfug ist :-)

Man kann es drehen wie man will:
Derartige Regeln darf man nicht als das "Gesetzbuch" ansehen, sondern 
als Guidelines, die man im Allgemeinen beachten sollte, die allerdings 
in Einzelfällen bei guten Gründen auch links liegen gelassen werden 
dürfen.

Und genau das ist mein Problem mit diesen automatischen Style-Guide 
Checkern, Code-Analysatoren etc. Sie sind nicht felxibel genug, den 
Ausnahmefall zu erkennen.

von Karl H. (kbuchegg)


Lesenswert?

oskar aus der mülltonne schrieb:

> Tim T. schrieb:
>> Und was spricht dagegen diese Suche in eine Funktion zu packen, die du
>> dann einfach mit einem return verlassen kannst?
>
> eine Sache die dagegen spricht ist, das du in der Funktion eventuell
> noch mit dem Array und i und j arbeiten möchtest.

OK.
Das kann die aufrufende Funktion aber auch mitgeben.

> Die Funktion könnte meinetwegen die Aufgabe "finde den ersten schwarzen
> Pixel und färbe in grün" haben.

Ist schon zuviel.
Die Funktion macht: Finde den ersten Pixel mit einer bestimmten Farbe

> Die Funktion durchsucht das 2D Array nach dem ersten Treffer. Eine
> Funktion kann maximal einen Wert zurückgeben. Also müsste man sich
> zusätzlich einen Typ (struct) definieren, der aus zwei ints besteht, x-
> und y-koordinate.

Entweder so, oder aber (da der Thread sowieso schon immer mehr in 
Richtung C++ abdriftet): 2 Argumente, Referenzen auf die x und y 
Positionen.

> Den Typ müsste man dan zurückgeben an eine Funktion,
> die dann den gefunden Pixel grün färbt.
>
> Das ist deutlich mehr Aufwand, als wenn man ein klares goto verwendet.

Ja.
Dafür kriegst du aber auch etwas: Eine find-Funktion die auch an anderer 
Stelle nutzbringend eingesetzt werden kann.

> Das Label muss ja nichteinmal am Funktionsende stehen, sondern kann
> direkt auf die verschachtelte For-Schleife folgen, dann gibt es ganz
> sicher keine Probleme mit dem Verständnis.

Schon richtig.
Aber spätestens wenn dieselbe Suchfunktionalität an 15 anderen Stellen 
im Programm auftaucht, ist eine dezidierte find-Funktion ganz klar der 
Winner.

Und gerade solche find-Funktionen sind von der Sorte, die fast überall 
auftauchen; die man aus 'Effizienzgründen' nicht in eine eigene Funktion 
verschiebt nur um ein halbes Jahr später einzusehen, dass man 
mitlerweile 20 mal denselben Code in 15 verschiedenen Funktionen hat, 
der im Grunde immer wieder nur dasselbe tut: ein Pixel suchen.


Solche Basisfunktionen haben eigentlich noch nie geschadet. Der 
Programmübersicht tun sie gut, die verwendenden Funktion werden kleiner 
und leichter durchschaubar, die Fehlerrate im Programm sinkt und, 
interessanterweise, die Laufzeit leidet NICHT darunter: Der Compiler 
inlined die Funktionen, da sie kurz und einfach genug sind.

von Tim T. (tim_taylor) Benutzerseite


Lesenswert?

oskar aus der mülltonne schrieb:

> eine Sache die dagegen spricht ist, das du in der Funktion eventuell
> noch mit dem Array und i und j arbeiten möchtest.
>
> Die Funktion könnte meinetwegen die Aufgabe "finde den ersten schwarzen
> Pixel und färbe in grün" haben.
> Die Funktion durchsucht das 2D Array nach dem ersten Treffer. Eine
> Funktion kann maximal einen Wert zurückgeben. Also müsste man sich
> zusätzlich einen Typ (struct) definieren, der aus zwei ints besteht, x-
> und y-koordinate. Den Typ müsste man dan zurückgeben an eine Funktion,
> die dann den gefunden Pixel grün färbt.

Ich hoffe das ist jetzt nicht dein Ernst:
1. Das man Sachen als Referenz übergeben kann und dann sehr wohl damit 
arbeiten, solltest du eigentlich wissen. Ich mach das praktisch immer 
sobald der Rückgabe-Datentyp etwas komplizierter als ein einfaches 
Ja/Nein oder sowas wird.
2. Bin ich in meinem Beispiel von einem globalen Array ausgegangen, wie 
der void-Parameter eigentlich zeigt.
3. Sollte die Funktion ja grade genau eine Aufgabe, eben das Suchen, 
erfüllen und nicht mehr.

von der mechatroniker (Gast)


Lesenswert?

Richtig.

Wenn man, vor die Aufgabe gestellt, in einem Satz die Aufgabe einer 
Funktion zusammenzufassen, spontan einen Satz mit "und" formuliert, 
stimmt was mit der Codestruktur nicht.

von oskar aus der mülltonne (Gast)


Lesenswert?

Deine Punkte sind natürlich alle richtig. Mein Beispiel war schlecht 
gewählt. Wenn man die Schleifen ohne treffer durchlaufen hat, würde der 
Code hinter dem Label ja trotzdem ausgeführt werden und somit ist das 
auch in dieser Hinsicht totaler Unsinn.

Das Beispiel von Robert Love ist wahrscheinlich besser zu gebrauchen:

>As a final argument, it does not let us cleanly do the usual stack-esque
wind and unwind, i.e.
1
  do A
2
  if (error)
3
    goto out_a;
4
  do B
5
  if (error)
6
    goto out_b;
7
  do C
8
  if (error)
9
    goto out_c;
10
  goto out;
11
  out_c:
12
  undo C;
13
  out_b:
14
  undo B;
15
  out_a:
16
  undo A;
17
  out:
18
  return ret;

Als Alternative könnte man hier im B-Zweig out_b(); out_a(), oder 
out(b); out(a), oder sonstwas shreiben. Wenn der out-Code allerdings so 
spezifisch ist, dass er nirgendwo anders gebraucht werden kann und wenn 
man vielleicht später nicht 3 if sondern 25 da stehen hat, dann ist das 
in der Tat viel übersichtlicher.

von oskar aus der mülltonne (Gast)


Lesenswert?

Tim T. schrieb:
> Ich hoffe das ist jetzt nicht dein Ernst:
> 1. Das man Sachen als Referenz übergeben kann und dann sehr wohl damit
> arbeiten, solltest du eigentlich wissen. Ich mach das praktisch immer
> sobald der Rückgabe-Datentyp etwas komplizierter als ein einfaches
> Ja/Nein oder sowas wird.
> 2. Bin ich in meinem Beispiel von einem globalen Array ausgegangen, wie
> der void-Parameter eigentlich zeigt.
> 3. Sollte die Funktion ja grade genau eine Aufgabe, eben das Suchen,
> erfüllen und nicht mehr.

zu 2./3.: ich habe mich gar nicht auf deinen Schnippsel bezogen, sondern 
auf meinen.

zu 1. Stimmt. Aus OO-Sicht habe ich mir überlegt das x- und y- 
koordinate einen Typ bilden, daher mein Punkt. Das habe ich wohl nicht 
zuende gedacht.

von Rolf Magnus (Gast)


Lesenswert?

oskar aus der mülltonne schrieb:
>>> Was schlägst du denn vor? structs zu definieren?
>>
>> Ja.
>
> Das ist glaube ich die übliche Variante. Allerdings natürlich
> Zweckentfremdung..

Warum? Die sind doch genau dafür da.

Karl heinz Buchegger schrieb:
> Man kann es drehen wie man will:
> Derartige Regeln darf man nicht als das "Gesetzbuch" ansehen, sondern
> als Guidelines, die man im Allgemeinen beachten sollte, die allerdings
> in Einzelfällen bei guten Gründen auch links liegen gelassen werden
> dürfen.

Hier ging es allerdings um MISRA. Wenn das halt geforder ist, kann man 
nachher schlecht sagen, man habe seinen Code "größtenteils nach MISRA" 
gemacht, es aber "da wo's blöd ist, auch mal ignoriert".

von Yalu X. (yalu) (Moderator)


Lesenswert?

oskar aus der mülltonne schrieb:
>> Da der Goto nach MISRA und vielen anderen Programmierrichtlinien aber
>> verboten ist, muss es meiner Meinung nach der Mehrfach-Return erst
>> recht sein.
>
> Das ist auch wieder eine sinnlose Vorschrift. Viel eher sollte dem
> Programmierer angeraten werden, Goto oder mehrfach-return nur zu
> verwenden, wenn es an der betreffenden Stelle einen nutzen gibt, der
> die Nachteile - also in der Regel unleserlichkeit - überwiegt.

Natürlich wäre es besser, man würde sämtliche Features einer Program-
miersprache erlauben, sofern ihr Einsatz im konkreten Kontext unter
Berücksichtung von Kriterien wie Lesbarkeit, Wartbarkeit, Effizienz usw.
einen Vorteil bringt.Dann bräuchte man solche Programmierrichtlinien wie
MISRA-C gar nicht.

Da aber nicht alle Programmierer diese Kriterien gleich bewerten und
weniger erfahrene Programmierer vielleicht gar nicht in der Lage sind,
sie zu bewerten, wurde bspw. MISRA-C so gestaltet, dass es keinen
Interpretationsspielraum offen lässt. Dies hat den zusätzlichen Vorteil,
dass die Eingaltung der Richtlinie mit automatischen Tools geprüft
werden kann.

Der Nachtteil an solchen streng definierten Vorgaben ist, dass sie in
manchen Fällen, wie in dem Beispiel mit den verschachtelten Schleifen,
über's Ziel hinausschießen und das Gegenteil von dem bewirken, wofür sie
eigentlich gemacht sind. Wenn dies aber nur in 5% aller Fälle passiert
und in den restlichen 95% tatsächlich eine Verbesserung der Codequalität
erreicht wird, hat die Richtlinie trotzdem ihren Zweck erfüllt. Das
dürfte zumindest der Gedanke der Erfinder solcher Richtlinien zu sein.

Bei weniger strengen Richtlinien, die viele Punkte dem Ermessen des
Programmierer überlassen und deswegen auch nicht (zumindest nicht
vollständig) automatisiert nachprüfbar sind, besteht die Gefahr, dass
ein "böses" Feature X, das eigentlich nur für Ausnahmefälle vorgesehen
ist, von einigen Programmierern ständig benutzt werden.

Es ist wie im Straßenverkehr: Dort gibt es die feste Regel, dass an
einer roten Ampel angehalten werden muss. Sie ist in den meisten Fällen
auch sinnvoll, um an stark befahrenen Kreuzungen den Verkehrsfluss der
einzelnen Fahrtrichtungen auszubalancieren. Nachts, wenn su gut wie kein
Verkehr herrscht, ist die Ampel aber eindeutig kontraproduktiv (sofern
sie nicht abgeschaltet wird). Trotzdem muss auch dann bei Rot angehalten
werden. Würde man die Verkehrsregel aufweichen, so dass bei Rot generell
nur dann angehalten werden muss, wenn es sinnvoll erscheint, könnte man
die Ampel wahrscheinlich genausogut abschaffen.

von oskar aus der mülltonne (Gast)


Lesenswert?

der mechatroniker schrieb:
> Richtig.
>
> Wenn man, vor die Aufgabe gestellt, in einem Satz die Aufgabe einer
> Funktion zusammenzufassen, spontan einen Satz mit "und" formuliert,
> stimmt was mit der Codestruktur nicht.

Abwegige Beispiele für Abstruse Anwendungsfälle auszudenken ist nunmal 
nicht das einfachste und dann kommt hat mal etwas praxisfernes dabei 
raus. Ich gebe zu, das ist kein Anwendungsfall mit dem man wirklich 
überzeugen kann und das war nicht gut ausgedacht. Schlag du doch was 
besseres vor.

Rolf Magnus schrieb:
> oskar aus der mülltonne schrieb:
>>>> Was schlägst du denn vor? structs zu definieren?
>>>
>>> Ja.
>>
>> Das ist glaube ich die übliche Variante. Allerdings natürlich
>> Zweckentfremdung..
>
> Warum? Die sind doch genau dafür da.

Strukturen sind  eine Zusammenfassung verschiedener Typen, die zusammen 
einen Typ bilden. Alle Member als static zu deklarieren ist 
wahrscheinlich so etwas wie ein Spezialfall und nicht der primäre Zweck.
Anders als in C++ kann ein struct in C keine Funktion als member haben.

von Karl H. (kbuchegg)


Lesenswert?

Rolf Magnus schrieb:

>> Man kann es drehen wie man will:
>> Derartige Regeln darf man nicht als das "Gesetzbuch" ansehen, sondern
>> als Guidelines, die man im Allgemeinen beachten sollte, die allerdings
>> in Einzelfällen bei guten Gründen auch links liegen gelassen werden
>> dürfen.
>
> Hier ging es allerdings um MISRA. Wenn das halt geforder ist, kann man
> nachher schlecht sagen, man habe seinen Code "größtenteils nach MISRA"
> gemacht, es aber "da wo's blöd ist, auch mal ignoriert".

Ich weiß.
Leider ist das so. Und ich sag hier ganz bewusst leider.

von Karl H. (kbuchegg)


Lesenswert?

Yalu X. schrieb:

> Es ist wie im Straßenverkehr: Dort gibt es die feste Regel, dass an
> einer roten Ampel angehalten werden muss.

Nun ist diese Regel aber auch willkürlich menschengemacht und muss 
beileibe nicht so sein.

> sie nicht abgeschaltet wird). Trotzdem muss auch dann bei Rot angehalten
> werden.

Bei uns. Ja.

> Würde man die Verkehrsregel aufweichen, so dass bei Rot generell
> nur dann angehalten werden muss, wenn es sinnvoll erscheint, könnte man
> die Ampel wahrscheinlich genausogut abschaffen.

Nicht wirklich. 'aufweichen' ist hier wieder relativ.

USA Reisende kennen das:
In den USA darf man in einigen Bundesstaaten (allen?) bei einer roten 
Ampel rechts abbiegen, sofern es der Querverkehr zulässt und es an der 
Ampel kein Zusatzschild gibt, welches das explizit verbietet.

Gegenüber unseren Verkehrsregeln ist das eine Aufweichung, allerdings 
eine sinnvolle.

von Rolf Magnus (Gast)


Lesenswert?

Karl heinz Buchegger schrieb:
> USA Reisende kennen das:
> In den USA darf man in einigen Bundesstaaten (allen?) bei einer roten
> Ampel rechts abbiegen, sofern es der Querverkehr zulässt und es an der
> Ampel kein Zusatzschild gibt, welches das explizit verbietet.
>
> Gegenüber unseren Verkehrsregeln ist das eine Aufweichung, allerdings
> eine sinnvolle.

Das gab's doch bei uns auch, nur mit umgekehrten Schildern. Also wenn 
ein Schild mit einem Grünpfeil da steht, darf man auch bei rot rechts 
abbiegen. Interessantes zur Sinnhaftigkeit dessen kann man nachlesen 
unter: http://de.wikipedia.org/wiki/Grünpfeil#Geschichte

oskar aus der mülltonne schrieb:
> Strukturen sind  eine Zusammenfassung verschiedener Typen, die zusammen
> einen Typ bilden. Alle Member als static zu deklarieren ist
> wahrscheinlich so etwas wie ein Spezialfall und nicht der primäre
> Zweck.

Wo habe ich denn was von static geschrieben, und warum sollte ich die 
static machen wollen? Davon abgesehen: In C kann man Struktur-Member gar 
nicht static machen.

von Manual Transmission (Gast)


Lesenswert?

Karl heinz Buchegger schrieb:
> USA Reisende kennen das:
> In den USA darf man in einigen Bundesstaaten (allen?) bei einer roten
> Ampel rechts abbiegen, sofern es der Querverkehr zulässt und es an der
> Ampel kein Zusatzschild gibt, welches das explizit verbietet.
>
> Gegenüber unseren Verkehrsregeln ist das eine Aufweichung, allerdings
> eine sinnvolle.

Man darf nur nicht Gas- und Bremspedal verwechseln...

von oskar aus der mülltonne (Gast)


Lesenswert?

Rolf Magnus schrieb:
> Wo habe ich denn was von static geschrieben, und warum sollte ich die
> static machen wollen? Davon abgesehen: In C kann man Struktur-Member gar
> nicht static machen.

Oha, das wusste ich gar nicht (mehr). Weil es keinen Sinn macht einen 
'namespace' der Konstenten enthalten soll mehrfach und evtl. mit 
verschiedenen werten zu instanzieren oder das zu erlauben.

von Rolf Magnus (Gast)


Lesenswert?

oskar aus der mülltonne schrieb:
> Weil es keinen Sinn macht einen 'namespace' der Konstenten enthalten
> soll mehrfach und evtl. mit verschiedenen werten zu instanzieren oder
> das zu erlauben.

Konstanten? Es ging doch um von einem Bus empfangene Daten.
Ich sehe das so: Wenn du die Einteilung z.B. nach Sender machst, dann 
erzeugst du eben für jeden Sender eine Struktur, in der die von diesem 
kommenden Daten zusammengefaßt werden. Ob die jetzt mehrfach 
instanziiert wird oder nur einmal, ist an der Stelle erstmal egal.

von oskar aus der mülltonne (Gast)


Lesenswert?

Rolf Magnus schrieb:
> oskar aus der mülltonne schrieb:
>> Weil es keinen Sinn macht einen 'namespace' der Konstenten enthalten
>> soll mehrfach und evtl. mit verschiedenen werten zu instanzieren oder
>> das zu erlauben.
>
> Konstanten? Es ging doch um von einem Bus empfangene Daten.
> Ich sehe das so: Wenn du die Einteilung z.B. nach Sender machst, dann
> erzeugst du eben für jeden Sender eine Struktur, in der die von diesem
> kommenden Daten zusammengefaßt werden. Ob die jetzt mehrfach
> instanziiert wird oder nur einmal, ist an der Stelle erstmal egal.

Ja so macht das natürlich Sinn. Ich habe das Problem so verstanden, dass 
es sehr viele Konstanten gibt, die die Steuerbefehle darstellen, die 
über den Bus gesendet werden. So wie
1
#define SKIP_ROM 0xCC
 beim 1wire-Bus.

von Yalu X. (yalu) (Moderator)


Lesenswert?

Karl heinz Buchegger schrieb:
>> Würde man die Verkehrsregel aufweichen, so dass bei Rot generell
>> nur dann angehalten werden muss, wenn es sinnvoll erscheint, könnte man
>> die Ampel wahrscheinlich genausogut abschaffen.
>
> Nicht wirklich. 'aufweichen' ist hier wieder relativ.
>
> USA Reisende kennen das:
> In den USA darf man in einigen Bundesstaaten (allen?) bei einer roten
> Ampel rechts abbiegen, sofern es der Querverkehr zulässt und es an der
> Ampel kein Zusatzschild gibt, welches das explizit verbietet.
>
> Gegenüber unseren Verkehrsregeln ist das eine Aufweichung, allerdings
> eine sinnvolle.

Ich würde das nicht als "Aufweichung", sondern eher als "Lockerung"
bezeichnen. Nach den USA-Verkehrsregeln muss der Fahrer bei Rot zwar
nicht immer anhalten, jedoch sind die Ausnahmen klar spezifiziert und
überhaupt nicht weich.

Übertragen auf Programmierrichtlinien würde dies bedeuten (nur als
Beispiel):

Goto darf normalerweise nicht verwendet werden. Die einzigen Ausnahmen
sind:
- Verschachtelten Schleifen dürfen mit Goto verlassen werden. Das
  Sprungziel muss dabei die Position direkt nach der äußersten zu
  verlassenden Schleife sein.
- ...

Auf diese Weise sind sinnvolle Ausnahmen zugelassen, liegen aber nicht
im Ermessen des Programmieres, sondern sind klar geregelt und deswegen
auch nachprüfbar. Jetzt müsste sich jetzt nur noch jemand finden, der
ein solches detaillierteres Regelwerk zusammenstellt und am besten noch
ein Prüftool dazu schreibt. Das wäre gerade für wenig erfahrene Program-
mierung eine große Hilfe, ihre Codequalität ein gutes Stück zu erhöhen.

Es sind ja vor allem die wenig erfahrenen Programmierer, für die solche
Richtlinien gemacht sind. Von alten Hasen sollte man erwarten, dass sie
das alles schon aus dem Gefühl heraus richtig machen und auch in der
Lage sind, Code, der nach einem leicht abweichenden Muster geschrieben
ist, trotzdem ohne Probleme zu verstehen.

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.