Akleson
08-05-2006, 11:09
Hallo
Ich wollte für ein Bildverarbeitungsproblem (für ein Echtzeitsystem) Berechnungen, die derzeit mit vector laufen auf valarray umstellen. In verschiedenen Büchern und Texten im Web werden diese als für numerische Berechnungen optimierte "Arrays" angepriesen. Leider kann ich das bei mir hier nicht ganz nachvollziehen. Im Gegenteil ich hab hier ein einfaches Beispiel bei dem sie deutlich langsamer sind.
Hier ist mal mein kleines Testprogramm
#include <iostream>
#include <valarray>
#include <vector>
#include <cstdlib>
{ ... schnipp schnapp .. }
int main() {
{ ... schnipp schnapp .. }
vector<float> vFloat(tSize);
vector<int> vInt(tSize);
tTime.set();
for (int r = 0; r != Runs; ++r) {
for (size_t i = 0; i != vFloat.size(); ++i) {
vFloat[i] *= fFloat;
}
}
tDur.set(tTime);
cout << endl;
cout << "Vector: vector<float> elementweise mit float mulitpliziert" << endl;
cout << "Vector: size=" << vFloat.size() << " runs=" << Runs << " duration=" << tDur.get() << endl;
tTime.set();
for (int r = 0; r != Runs; ++r) {
for (size_t i = 0; i != vInt.size(); ++i) {
vInt[i] *= 4;
vInt[i] /= 5;
}
}
tDur.set(tTime);
cout << endl;
cout << "Vector: vector<int> elementweise * 4 / 5" << endl;
cout << "Vector: size=" << vInt.size() << " runs=" << Runs << " duration=" << tDur.get() << endl;
//################################################## ####
valarray<float> vaFloat(tSize);
valarray<int> vaInt(tSize);
tTime.set();
for (int r = 0; r != Runs; ++r) {
vaFloat *= fFloat;
}
tDur.set(tTime);
cout << endl;
cout << "Valarray: valarray<float> elementweise mit float mulitpliziert" << endl;
cout << "Valarray: size=" << vaFloat.size() << " runs=" << Runs << " duration=" << tDur.get() << endl;
tTime.set();
for (int r = 0; r != Runs; ++r) {
vaInt *= 4;
vaInt /= 5;
}
tDur.set(tTime);
cout << endl;
cout << "Valarray: valarray<int > elementweise * 4 / 5" << endl;
cout << "Valarray: size=" << vaInt.size() << " runs=" << Runs << " duration=" << tDur.get() << endl;
}
Ich habe dieses auf ein Linux PC (Pentium 4) compiliert (gcc 3.4.3,-O2) und ausgeführt. Das Ergebniss war unerwartet:
Vector: vector<float> elementweise mit float mulitpliziert
Vector: size=1000000 runs=100 duration=2047.86
Vector: vector<int> elementweise * 4 / 5
Vector: size=1000000 runs=100 duration=2130.25
Valarray: valarray<float> elementweise mit float mulitpliziert
Valarray: size=1000000 runs=100 duration=2051.39
Valarray: valarray<int > elementweise * 4 / 5
Valarray: size=1000000 runs=100 duration=7566.39
also bei Int werten ist valarray um den Faktor 4 langsamer als ein von Hand multiplizierter Vektor. Und auch bei der Float Variante gewinne ich keinerlei Zeit. Ich hab auch mit Optionen wie -msse u.ä. oder -march probiert mit dem gleichen Ergebnis.
Kann mir evtl jemand sagen, ob ich etwas falsch verstanden habe oder einen logischen Denkfehler unterliege? Ich kann mir diese Ergebnisse nur noch erklären mit einer schlechten Implementation von valarrays in der mir vorliegenden Version.
Gruss Hannes
Ich wollte für ein Bildverarbeitungsproblem (für ein Echtzeitsystem) Berechnungen, die derzeit mit vector laufen auf valarray umstellen. In verschiedenen Büchern und Texten im Web werden diese als für numerische Berechnungen optimierte "Arrays" angepriesen. Leider kann ich das bei mir hier nicht ganz nachvollziehen. Im Gegenteil ich hab hier ein einfaches Beispiel bei dem sie deutlich langsamer sind.
Hier ist mal mein kleines Testprogramm
#include <iostream>
#include <valarray>
#include <vector>
#include <cstdlib>
{ ... schnipp schnapp .. }
int main() {
{ ... schnipp schnapp .. }
vector<float> vFloat(tSize);
vector<int> vInt(tSize);
tTime.set();
for (int r = 0; r != Runs; ++r) {
for (size_t i = 0; i != vFloat.size(); ++i) {
vFloat[i] *= fFloat;
}
}
tDur.set(tTime);
cout << endl;
cout << "Vector: vector<float> elementweise mit float mulitpliziert" << endl;
cout << "Vector: size=" << vFloat.size() << " runs=" << Runs << " duration=" << tDur.get() << endl;
tTime.set();
for (int r = 0; r != Runs; ++r) {
for (size_t i = 0; i != vInt.size(); ++i) {
vInt[i] *= 4;
vInt[i] /= 5;
}
}
tDur.set(tTime);
cout << endl;
cout << "Vector: vector<int> elementweise * 4 / 5" << endl;
cout << "Vector: size=" << vInt.size() << " runs=" << Runs << " duration=" << tDur.get() << endl;
//################################################## ####
valarray<float> vaFloat(tSize);
valarray<int> vaInt(tSize);
tTime.set();
for (int r = 0; r != Runs; ++r) {
vaFloat *= fFloat;
}
tDur.set(tTime);
cout << endl;
cout << "Valarray: valarray<float> elementweise mit float mulitpliziert" << endl;
cout << "Valarray: size=" << vaFloat.size() << " runs=" << Runs << " duration=" << tDur.get() << endl;
tTime.set();
for (int r = 0; r != Runs; ++r) {
vaInt *= 4;
vaInt /= 5;
}
tDur.set(tTime);
cout << endl;
cout << "Valarray: valarray<int > elementweise * 4 / 5" << endl;
cout << "Valarray: size=" << vaInt.size() << " runs=" << Runs << " duration=" << tDur.get() << endl;
}
Ich habe dieses auf ein Linux PC (Pentium 4) compiliert (gcc 3.4.3,-O2) und ausgeführt. Das Ergebniss war unerwartet:
Vector: vector<float> elementweise mit float mulitpliziert
Vector: size=1000000 runs=100 duration=2047.86
Vector: vector<int> elementweise * 4 / 5
Vector: size=1000000 runs=100 duration=2130.25
Valarray: valarray<float> elementweise mit float mulitpliziert
Valarray: size=1000000 runs=100 duration=2051.39
Valarray: valarray<int > elementweise * 4 / 5
Valarray: size=1000000 runs=100 duration=7566.39
also bei Int werten ist valarray um den Faktor 4 langsamer als ein von Hand multiplizierter Vektor. Und auch bei der Float Variante gewinne ich keinerlei Zeit. Ich hab auch mit Optionen wie -msse u.ä. oder -march probiert mit dem gleichen Ergebnis.
Kann mir evtl jemand sagen, ob ich etwas falsch verstanden habe oder einen logischen Denkfehler unterliege? Ich kann mir diese Ergebnisse nur noch erklären mit einer schlechten Implementation von valarrays in der mir vorliegenden Version.
Gruss Hannes