Ich habe ein C++-Programm, das Daten aus einer Binärdatei einliest, und ursprünglich habe ich die Daten in std::vector<char*> data
. Ich habe meinen Code dahingehend geändert, dass ich jetzt Strings anstelle von char* verwende, so dass std::vector<std::string> data
. Einige Änderungen, die ich vornehmen musste, waren der Wechsel von strcmp
a compare
zum Beispiel.
Ich habe jedoch festgestellt, dass sich meine Ausführungszeit drastisch verlängert hat. Für eine Beispieldatei benötigte ich bei Verwendung von char* 0,38s und nach der Konvertierung in string 1,72s auf meinem Linux-Rechner. Ein ähnliches Problem habe ich auf meinem Windows-Rechner beobachtet, wo die Ausführungszeit von 0,59s auf 1,05s anstieg.
Ich glaube, dass diese Funktion die Ursache für die Verlangsamung ist. Sie ist Teil der Konverterklasse, beachten Sie die privaten Variablen, die mit _
am Ende des Variablennamens. Ich habe hier eindeutig Speicherprobleme und stecke zwischen C- und C++-Code fest. Ich möchte, dass dies C++-Code ist, also habe ich den Code unten aktualisiert.
I Zugang ids_
y names_
viele Male in einer anderen Funktion, daher ist die Zugriffsgeschwindigkeit sehr wichtig. Durch die Erstellung eines map
anstelle von zwei separaten Vektoren, konnte ich schnellere Geschwindigkeiten mit stabilerem C++-Code erreichen. Vielen Dank an alle!
Beispiel NewList.Txt
2515 ABC 23.5 32 -99 1875.7 1
1676 XYZ 12.5 31 -97 530.82 2
279 FOO 45.5 31 -96 530.8 3
OLD-Code:
void converter::updateNewList(){
FILE* NewList;
char lineBuffer[100];
char* id = 0;
char* name = 0;
int l = 0;
int n;
NewList = fopen("NewList.txt","r");
if (NewList == NULL){
std::cerr << "Error in reading NewList.txt\n";
exit(EXIT_FAILURE);
}
while(!feof(NewList)){
fgets (lineBuffer , 100 , NewList); // Read line
l = 0;
while (!isspace(lineBuffer[l])){
l = l + 1;
}
id = new char[l];
switch (l){
case 1:
n = sprintf (id, "%c", lineBuffer[0]);
break;
case 2:
n = sprintf (id, "%c%c", lineBuffer[0], lineBuffer[1]);
break;
case 3:
n = sprintf (id, "%c%c%c", lineBuffer[0], lineBuffer[1], lineBuffer[2]);
break;
case 4:
n = sprintf (id, "%c%c%c%c", lineBuffer[0], lineBuffer[1], lineBuffer[2],lineBuffer[3]);
break;
default:
n = -1;
break;
}
if (n < 0){
std::cerr << "Error in processing ids from NewList.txt\n";
exit(EXIT_FAILURE);
}
l = l + 1;
int s = l;
while (!isspace(lineBuffer[l])){
l = l + 1;
}
name = new char[l-s];
switch (l-s){
case 2:
n = sprintf (name, "%c%c", lineBuffer[s+0], lineBuffer[s+1]);
break;
case 3:
n = sprintf (name, "%c%c%c", lineBuffer[s+0], lineBuffer[s+1], lineBuffer[s+2]);
break;
case 4:
n = sprintf (name, "%c%c%c%c", lineBuffer[s+0], lineBuffer[s+1], lineBuffer[s+2],lineBuffer[s+3]);
break;
default:
n = -1;
break;
}
if (n < 0){
std::cerr << "Error in processing short name from NewList.txt\n";
exit(EXIT_FAILURE);
}
ids_.push_back ( std::string(id) );
names_.push_back(std::string(name));
}
bool isFound = false;
for (unsigned int i = 0; i < siteNames_.size(); i ++) {
isFound = false;
for (unsigned int j = 0; j < names_.size(); j ++) {
if (siteNames_[i].compare(names_[j]) == 0){
isFound = true;
}
}
}
fclose(NewList);
delete [] id;
delete [] name;
}
C++ CODE
void converter::updateNewList(){
std::ifstream NewList ("NewList.txt");
while(NewList.good()){
unsigned int id (0);
std::string name;
// get the ID and name
NewList >> id >> name;
// ignore the rest of the line
NewList.ignore( std::numeric_limits<std::streamsize>::max(), '\n');
info_.insert(std::pair<std::string, unsigned int>(name,id));
}
NewList.close();
}
UPDATE: Folgefrage: Engpass beim Vergleich von Zeichenketten und danke für die sehr nützliche Hilfe! Ich werde diese Fehler in Zukunft nicht mehr machen!