Forum: PC-Programmierung von C nach C++


von masl (Gast)


Lesenswert?

Hallo,
ich arbeite gerade an einem relativ umfangreichen (Hobby-)PC-Projekt.

Ich bin in C fit, bin auch beruflich im Embedded-Umfeld unterwegs.
Die objektorientierte Denkweise ist mir auch vertraut, ich hab mit Java 
schon mal was mittelgroßes realisiert. Allerdings bin ich kein Fan von 
diesem Bytecodezeugs und virtuellen Maschinen, die erst installiert 
werden müssen.

Zu Lernzwecken würde ich nun gerne mit C++ arbeiten.
Das ist relativ Neuland für mich.
Aber am PC hab ich ja genug Resourcen, also wieso nicht die 
Annehmlichkeiten nutzen, die unter C oft mühselig "per Hand" gelöst 
werden müssen?

Nun hab ich aber oft Probleme, die "richtige" Lösung für meine Probleme 
zu finden (wobei richtig natürlich Ansichtssache ist).
Wichtig ist mir, das Problem C++-like zu lösen.

Konkretes Beispiel:
Ich lese eine Datei zeilenweise ein, die Datensätze, getrennt durch 
Tabulatoren, enthält.
Unter C würde ich nun mit verschiedenen Funktionen auf mein char-array 
losgehen, um die Werte aufzudröseln und in Variablen abzulegen. (also so 
strtok- und atoi-Geschichten).

Unter C++ sollte das ja wohl einfacher gehen, also mal nach "C++ string 
tokenizer" gegoogelt.
Auf 
http://stackoverflow.com/questions/53849/how-do-i-tokenize-a-string-in-c 
werden sehr viele Lösungsvorschläge präsentiert, ich hab mich noch nicht 
in alle hineingedacht.
Was mich stört: entweder wird das Problem C-like angegangen 
(herumhantieren mit char-arrys und den altbekannten Funktion, mit allen 
Vor- und Nachteilen) oder dicke Bibliotheken eingebunden (Boost, Qt).

Funktionieren würde sich vieles, aber mir gehts darum ordentliches C++ 
zu schreiben, kein Mischmasch und keine Bastellösungen.
Dafür soll mir das Projekt ja dienen...

Was macht ihr denn in so einer Situation?
Bibliotheken einbinden ohne Ende?
Selber Work-arounds und Wrapper schreiben?
C-style programmieren?

Mit diesem C++ hab ich irgendwie noch so meine Probleme, wahrscheinlich 
weil einfach so viele Lösungen angeboten werden...

Viele Grüße,
masl

von Rene S. (Firma: BfEHS) (rschube)


Lesenswert?

Geht es dir um das lernen von C++ oder um eine Probelmlösung?
Ich würde verschiedene Ansätze austesten.
1. Jedes C(ANSI.89) Programm ist ein C++ Programm, aber nicht umgekehrt.
Also C-Style schreiben und gucken...
2. UML-Designer verwenden und C++ Template erzeugen und ausfüllen

oder 3. Bücher / E-Books besorgen und lesen, lesen, lesen...

Gruß aus Berlin

von Basti M. (counterfeiter)


Lesenswert?

Seh hier kein Problem. Schreib dir eine Klasse die strtok- und 
atoi-Geschichten ausführt und dann haste dein C++.
Oder benutz die tausend anderen Möglichkeiten. Ein richtig Richtig gibt 
es hier wohl nicht...

von masl (Gast)


Lesenswert?

Rene Schube schrieb:
> Geht es dir um das lernen von C++ oder um eine Probelmlösung?

Schwer zu sagen, um was es mir genau geht.

Ein wirkliches Problem das ich lösen muss hab ich nicht. Ich hab mir ein 
Projekt ausgedacht um mal was mit C++ zu machen.

C++ lernen: Jein. Ich kann C++, im Sinne von "Ich kenne die Syntax. Ich 
bin mit der objektorientierten herngehensweise vertraut. Ich weis wie 
Vererbung und Polymorphie funktionieren. Ich weiß was ein 
Konstruktor/Dekonstruktor macht. Ich kenne Überladung von Operanden und 
Funktionen.".

Was mir fehlt ist der gute C++-Stil. Man kann die Probleme auf so 
vielfältige Weise lösen, dass ich als Anfänger erstmal erschlagen bin.
Man kann fast alles erstmal "oldschool" lösen. Das will ich nicht, für 
das brauch ich kein C++. Ich, mit meinem C-Hintergrund, habs da echt 
schwer nicht in die alten Verhaltensmustern zurückzufallen.

Es gibt für jedes Trivialproblem zig Bibliotheken, das hab ich gerade an 
meinem Beispiel mit der String-Zerlegung gesehen.
Ich halte es aber für nicht elegant und unüberschaubar, zig Bibliotheken 
für jeden Furz einzubinden.

Die STL wär mir erstmal am Liebsten. Leider dachte ich (mit meinem 
C-Hintergrund) bisher, die STL wäre die Eierlegende Wollmilchsau, was 
sie aber leider nicht ist. Also bleibt wieder nur, diese 
Unzulänglichkeiten zu umschiffen ("Bastellösungen") wie in C bisher 
notwendig war, oder wieder auf andere Bibliotheken auszuweichen.

Mir fehlt da einfach die Praxis...

von Rene S. (Firma: BfEHS) (rschube)


Lesenswert?

Na dann würde ich aus meinen Ansätzen den 2. versuchen.

UML-Designer -> Code-Templates ...

Je nach dem Designer erhält man eine vernünftige Struktur und im Prinzip 
ein lauffähiges Programm-Gerüst.
-> http://de.wikipedia.org/wiki/UML-Werkzeug#Codeerzeugung

Die grosse Suchmaschine findest auch reichlich Infos: "UML-Designer C++"

Wenn die Grundlagen sitzten ist es, denke ich der einfachste Weg.

von Karl H. (kbuchegg)


Lesenswert?

masl schrieb:

> Die STL wär mir erstmal am Liebsten.

Na, dann machs halt mit der STL.

Du hast eine wunderbare std::string Klasse.
Sieh dir an, welche Member die hat und such dir einen Weg, wie du mit 
den vorhandenen Funktionen deine gewünschte Funktionalität 
zurechtpfriemeln kannst.


Entweder du willst fertige Tokenizer. Dann musst du zu den großen 
Bibliotheken gehen. Oder du nimmst eine Nummer kleiner und setzt dir mit 
wenig Aufwand aus den Primtiv-Basisklassen das gewünschte zusammen.

Einen String an Tabulatoren in Einzelteile aufzubrechen ist ja jetzt 
nicht wirklich Raketentechnik, wenn man Funktionen wie find, erase, 
substr zur Verfügung hat. Die Eregebnisse könnte man zb in einen 
vector<string> stecken und die Sache ist gegessen.

> Unzulänglichkeiten zu umschiffen ("Bastellösungen") wie in C bisher
> notwendig war,

Ne, ne.
Langsam.
Alleine dadurch, dass dir die std::string schon mal das ganze dynamische 
Memory Management abnimmt, sparst du dir gegenüber einer reinen C-Lösung 
schon mal 80% vom Code und 95% aller dabei möglichen Fehler. Und der 
Rest ist eine Kombination aus ein paar Member Funktionen von std::string 
uns std::vector mit einer Schleife drumherum. Also soooo wild ist das 
auch wieder nicht. STL bedeutet ja nicht, dass es für jeden erdenklichen 
Aufgabenfall eine fix&fertige Lösung gibt.

von Vlad T. (vlad_tepesch)


Lesenswert?

schau dir Qt an.
Da ist es ziemlich straight forward.
1
QFile file("dateiname.tsv");
2
QVector<QVector<float>> dataFile;
3
4
if( file.open(QIODevice::ReadOnly) )
5
{
6
  QTextStream input(inputfile);
7
8
  while(!file.atEnd()){
9
    QString line = input.readLine();
10
    QStringList fields = line.split("\t");
11
    QVector<float> dataSet;
12
    foreach(auto& elem, fields){
13
      dataset.append(elem.toFloat());
14
    }
15
    dataFile.append(dataset);
16
  }
17
  
18
}

von Peter II (Gast)


Lesenswert?

Vlad Tepesch schrieb:
> Da ist es ziemlich straight forward.

ja und leider nicht so schnell wie jeden billige C version.

> QStringList fields = line.split("\t");
hier wird eine array angelegt wo der gleiche Inhalt wie im String drin 
steht.

Man kopiert also alle daten und braucht extra nach eine 
verwaltungsstrukur.

In C geht man einfach auf dem String durch und nimmt die elemente die 
man braucht.

Mir ist klar das es auf einem normales PC kein unterschied merkbar ist, 
aber mir stört so eine Resourcenverschwendung. Somal das ganze in C 
nicht (viel) mehr code ist.

von Karl H. (kbuchegg)


Lesenswert?

Peter II schrieb:
> Vlad Tepesch schrieb:
>> Da ist es ziemlich straight forward.
>
> ja und leider nicht so schnell wie jeden billige C version.

Solange die Strings von einem File kommen, ist das piep schnurz egal.
Ob die Zerlegung 50 oder 150 Nanosekunden dauert, interessiert 
heutzutage industriell keinen mehr. Wichtiger ist, dass es fehlerfrei 
und schnell programmiert werden kann.

von Vlad T. (vlad_tepesch)


Lesenswert?

Peter II schrieb:
> In C geht man einfach auf dem String durch und nimmt die elemente die
> man braucht.

klar geht das effizienter und Ressourcensparender.
Das mag sogar wichtig sein, wenn man riesige Datein einliest.

Großer Vorteil ist jedoch (gerade für Programmieranfänger), dass man 
recht wenig falsch machen kann, da sich die Klassen um die 
Speicherverwaltung kümmern.
Die Wahrscheinlichkeit sich irgendwo was durch Buffer-Overruns 
kaputtzuschreiben geht gegen 0.

von Peter II (Gast)


Lesenswert?

Karl Heinz Buchegger schrieb:
> Solange die Strings von einem File kommen, ist das piep schnurz egal.
> Ob die Zerlegung 50 oder 150 Nanosekunden dauert, interessiert
> heutzutage industriell keinen mehr. Wichtiger ist, dass es fehlerfrei
> und schnell programmiert werden kann.

Filesystem können auch daten mit 500Mbyte/s liefern, dann hat die CPU 
schon zu tun.

Wenn ich mit den gleichen Aufwand es schneller programmieren kann, warum 
sollte ich denn resourcen verschwenden nur weil es gerade modern ist?

von Peter II (Gast)


Lesenswert?

Vlad Tepesch schrieb:
> Großer Vorteil ist jedoch (gerade für Programmieranfänger), dass man
> recht wenig falsch machen kann, da sich die Klassen um die
> Speicherverwaltung kümmern.
> Die Wahrscheinlichkeit sich irgendwo was durch Buffer-Overruns
> kaputtzuschreiben geht gegen 0.

er ist aber kein Programmieranfänger, er möchte nur wissen wie man es in 
C++ machen würde. Und hier sehen ich keine sinnvolle verwendung für C++ 
und würde es genauso wie in C machen.

von Karl H. (kbuchegg)


Lesenswert?

Peter II schrieb:

> Wenn ich mit den gleichen Aufwand es schneller programmieren kann, warum
> sollte ich denn resourcen verschwenden nur weil es gerade modern ist?

:-)

Das haben wir alles in den letzten 40 Jahren gesehen. Die Anzahl der 
Programmabstürze, fehlerhaften Daten, Möglichkeiten zur Manipulation ist 
legendär. Aber die Hauptsache man hat es schnell und resourcenschonend 
geschrieben :-)
Hautzutage hat sich Gott sei Dank der Fokus verschoben. 'Speed um jeden 
Preis' ist heute kein Thema mehr.

> Wenn ich mit den gleichen Aufwand

Genau da liegt der Trugschluss. Bis du in deinem C tatsächlich 'das 
gleiche Resultat hast', ist dein persönlicher Aufwand in C beträchtlich 
höher! Es reicht nicht, wenn das C-Programm ungefähr dasselbe macht, wie 
das C++ Programm. Es muss sich auch in Fehlersituationen gleichwertig 
Verhalten (nämlich den Fehler abfangen und etwas sinnvolles damit tun). 
Und dann wird deine 'schnell-schnell' Lösung dann nämlich plötzlich gar 
nicht mehr so 'schnell-schnell'.

Und das fängt schon mit dieser ganz banalen Zeile an
1
    QString line = input.readLine();

bis du DAS in C #gleichwertig# hast, hab ich meine C++ Lösung schon 
ausgeliefert :-)


(Das geht nicht gegen dich persönlich.)

von Peter II (Gast)


Lesenswert?

Karl Heinz Buchegger schrieb:
> Und das fängt schon mit dieser ganz banalen Zeile an
> QString line = input.readLine();
> bis du DAS in C 'gleichwertig' hast, hab ich meine C++ Lösung schon
> ausgeliefert :-)

gegen die zeile habe ich auch nichts - die Trick besteht ja daran immer 
das zu verwenden was jeweil sinnvoll ist.

Es ging mir nicht um das einlesen der Zeile sondern um das Parsen und da 
bin ich mit C genauso schnell.

von Peter II (Gast)


Lesenswert?

@Karl Heinz Buchegger

es ist irgendwie dumm das du in letzter zeit die Beiträge noch 
nachträglich editierst, das macht die Beantwortung nicht einfach.

von Karl H. (kbuchegg)


Lesenswert?

Peter II schrieb:
> Karl Heinz Buchegger schrieb:
>> Und das fängt schon mit dieser ganz banalen Zeile an
>> QString line = input.readLine();
>> bis du DAS in C 'gleichwertig' hast, hab ich meine C++ Lösung schon
>> ausgeliefert :-)
>
> gegen die zeile habe ich auch nichts - die Trick besteht ja daran immer
> das zu verwenden was jeweil sinnvoll ist.
>
> Es ging mir nicht um das einlesen der Zeile sondern um das Parsen und da
> bin ich mit C genauso schnell.

Es spricht ja auch nichts dagegen, auch in C++ dieses Parsen auf einem 
std::string zu machen und sich die gefundenen Positionen in einem size_t 
Array zu merken. Die Möglichkeiten sind ja da.

Wenn es dir aber eben nicht reicht, das Parsen quasi 'in place' im 
String zu machen, sondern wenn du die Strings dann tatsächlich einzeln 
benötigst, dann bietet dir C++ auch dann Möglichkeiten, welche du in C 
so erst mal nicht hast.


Gerade dann, wenn es eben darum geht, mal schnell eben ein Werkzeug zu 
schreiben, welches ein gerade anfallendes Problem kurzfristig löst, ist 
man mit einem objektorientierten Ansatz meistens um einiges schneller, 
eben weil man sich nicht um die kleinen Stolpersteine kümmern muss.

von Udo S. (urschmitt)


Lesenswert?

Karl Heinz Buchegger schrieb:
> Hautzutage hat sich Gott sei Dank der Fokus verschoben. 'Speed um jeden
> Preis' ist heute kein Thema mehr.

Unterschreibe ich zu 100%. Obwohl es immer sinnvoll ist im Hinterkopf zu 
wissen wie günstig/ungünstig bzgl. Laufzeit eine Lösung ist. Zumindest 
tendenziell.
In größeren Softwareprojekten sind üblicherweise <1% des Codes 
Zeitrelevant.
Die Kunst ist es nicht Code zu optimieren, bei dem es sch--- egal ist ob 
er in einer oder 10 µs ausgeführt wird, weil der User doch eine Sekunde 
braucht, sondern genau dieses 1% zu optimieren.

von Peter II (Gast)


Lesenswert?

Karl Heinz Buchegger schrieb:
> Es spricht ja auch nichts dagegen, auch in C++ dieses Parsen auf einem
> std::string zu machen und sich die gefundenen Positionen in einem size_t
> Array zu merken. Die Möglichkeiten sind ja da.

richtig, mich hat nur das split mit dem ereugen das Array gestört. Klar 
kann man auch mit einem iterator über einen std:string gehen dagen ist 
auch nichts zu sagen.

Man sollte nur halt wissen was alles bei so einem einfach split 
passiert.

von masl (Gast)


Lesenswert?

Hui, da hab ich ja was losgetreten :-)

Wenn mein Programm ein wenig langsamer läuft als ein reines C-Pendant 
dann kann ich damit leben.
Wie schon öfter erwähnt, wir sind a) auf einem modernen PC unterwegs
und b) haben wir (ich) nichts zeitkritisches zu Lösen. Hier wird eine 
Datei beim Programmstart eingelesen und geparsed.

Deswegen lege ich Wert darauf dass der Code möglichst leicht zu lesen 
ist (und damit leichter zu warten) und dass das Programm zuverlässiger 
(==weniger Fehleranfällig) wird.
Sonst könnt ich ja gleich bei C bleiben.

Trotzdem will ich natürlich nicht immer sofort den Holzhammer 
herausholen der alles passend macht wenns auch ein einfacheres Werkzeug 
tut.
Und dieses Wissen, wann welche Vorgehensweise angebracht ist, fehlt mir 
eben.
C++ bietet da eben ein weites Spektrum an Werkzeug"größen". Ich kann ein 
Problem sehr abstrakt angehen indem ich Klassen benutze die ihrerseits 
dutzende Klassen und Methoden kapseln und mir großen Komfort 
ermöglichen.
Ich kann aber auch direkt an den einzelnen Bits meiner Daten 
rumpfriemeln, wenn ich wollte, und alles "zu Fuss" machen.

Ich denke mal, es verlangt einiges an Übung und Erfahrung, das passende 
Werkzeug auszuwählen.
Ich habe hier auf einige interessante Meinungen gehofft, und diese auch 
erhalten.

Ich bin dann mal weiterüben :-) (erstmal nur mit STL)

von Hans (Gast)


Lesenswert?

Peter II schrieb:
> Filesystem können auch daten mit 500Mbyte/s liefern, dann hat die CPU
> schon zu tun.

schon, aber 99% der zeit wirst du die felder (strings) in andere typen 
umwandeln und nicht zeichen herumschieben.

daher ist der split vollkommen egal!

außerdem wirst du mit den eingaben auch was anderes machen als sie bloß 
umzuformatieren... sonst würde ich stark zur verwendung von awk raten :)

73

von Peter II (Gast)


Lesenswert?

Hans schrieb:
> schon, aber 99% der zeit wirst du die felder (strings) in andere typen
> umwandeln und nicht zeichen herumschieben.
>
> daher ist der split vollkommen egal!

kleinvieh mauch auch mist!

> außerdem wirst du mit den eingaben auch was anderes machen als sie bloß
> umzuformatieren... sonst würde ich stark zur verwendung von awk raten :)
wenn es nicht schnell sein muss nehme ich auch kein C/C++ mehr dann ist 
c# dran.

von Olaf (Gast)


Lesenswert?

> Hautzutage hat sich Gott sei Dank der Fokus verschoben. 'Speed um
> jeden Preis' ist heute kein Thema mehr.

Stimmt, heute gibt es schon Leute die laden ihr Handy taeglich auf und 
halten das fuer normal. Ich erlaube mir aber das fuer peinlich zu 
halten.

Olaf

von Karl H. (kbuchegg)


Lesenswert?

Olaf schrieb:
>> Hautzutage hat sich Gott sei Dank der Fokus verschoben. 'Speed um
>> jeden Preis' ist heute kein Thema mehr.
>
> Stimmt, heute gibt es schon Leute die laden ihr Handy taeglich auf und
> halten das fuer normal. Ich erlaube mir aber das fuer peinlich zu
> halten.

Was hat das eine mit dem anderen zu tun?

Ob sich ein Dialog in 1 Millisekunde oder in 1.5 Millisekunden 
schliesst, interessiert keine Sau. Beides ist für einen Benutzer "nicht 
merkbar".

von Peter II (Gast)


Lesenswert?

Karl Heinz Buchegger schrieb:
> Ob sich ein Dialog in 1 Millisekunde oder in 1.5 Millisekunden
> schliesst, interessiert keine Sau. Beides ist für einen Benutzer "nicht
> merkbar".

wenn die software 1Mil nutzer die damit einen höheren Stromverbrauch in 
diese zeit haben könnte man schon fast eine Windrad sparen.

von Le X. (lex_91)


Lesenswert?

Peter II schrieb:
> Karl Heinz Buchegger schrieb:
>> Ob sich ein Dialog in 1 Millisekunde oder in 1.5 Millisekunden
>> schliesst, interessiert keine Sau. Beides ist für einen Benutzer "nicht
>> merkbar".
>
> wenn die software 1Mil nutzer die damit einen höheren Stromverbrauch in
> diese zeit haben könnte man schon fast eine Windrad sparen.

Ach komm, das kannst du garnicht ernst meinen.
Der PC läuft bei den meißten eh einfach so zur Gaudi, weil keiner Lust 
auf runterfahrn und neu starten hat.

Keiner sagt hier dass man alles dreckig und ressourcenfressend 
programmieren muss.
Ihr tut ja alle als würde die Benutzung einer Bibliothek einen Overhead 
ohne Ende darstellen.

Aber wisst ihr was?
Genau so wie ihr niemals mit Assembler den C-Compiler in Sachen 
Optimierung schlagen werdet (jaja, zu 95% nicht) so werdet ihr mit 
Bytegepfriemel und LowLevel-Zugriffen wie in C üblich nicht die 
Performance der STL nachbilden können, zumindest nicht mit annähernd 
diesem Komfort und der Fehlertoleranz.
Denn, tut mir leid, den Leuten die solche Libs schreiben trau ich mehr 
zu als dem durchschnittlichen Forumuser.
Wieso also sich nicht auf Lösungen verlassen, die sich weltweit 
millionenfach bewährt haben?

von D. I. (Gast)


Lesenswert?

le x. schrieb:
> Wieso also sich nicht auf Lösungen verlassen, die sich weltweit
> millionenfach bewährt haben?

Na weil "ein Programm erst dann perfekt ist wenn man nichts mehr 
weglassen kann ohne die Funktion zu beeinträchtigen (tm)" ;)
Zumindest verkündet das ein einst berühmter Geist aus der technischen 
Prähistorie in latent aggressivem Ton regelmäßig :)

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.