您發佈的代碼中有兩個錯誤,我糾正了。
1)假設你總是希望要查詢兩個十六進制數字如果該值小於16,而不是10
2)QString::setNum
沒有過載炭,因此該值被提升到一個更大的類型。對於像128這樣的值,在簽名字符中爲負數,由於符號擴展,您將得到x0ffffffffffffff80
。
功能foo1
是你原來的代碼修復的錯誤,並foo2
是避免創建自轉換爲Unicode臨時QString
更優化的版本,後面是不是免費的,前面加上值的字符串需要額外的複製。
我使用QElapsedTimer
,因爲在我測試的Windows上它使用高分辨率PerformanceCounter時鐘。如果你在另一個平臺上,它可能不太準確。您可以在文檔中看到它可能使用的不同類型的時鐘。
將display_converted_string
設置爲true,如果您想要打印轉換後的字符串以驗證它們是否相同。
#include <QString>
#include <QByteArray>
#include <QElapsedTimer>
#include <iostream>
QByteArray foo1(QByteArray data)
{
QByteArray newData;
for (int i = 0; i < data.size(); i++) {
unsigned char c = data[i];
QString hex;
hex.setNum(c, 16);
if (c < 16) {
hex.prepend("x0");
} else {
hex.prepend("x");
}
newData.append(hex.toLatin1());
}
return newData;
}
QByteArray foo2(QByteArray data)
{
static const char digits[] = {'0','1','2','3','4','5','6','7',
'8','9','a','b','c','d','e','f'};
QByteArray newData;
newData.reserve(data.size() * 3);
for (int i = 0; i < data.size(); i++)
{
unsigned char c = data[i];
newData.append('x');
newData.append(digits[(c >> 4) & 0x0f]);
newData.append(digits[c & 0x0f]);
}
return newData;
}
int main()
{
const int iterations = 10000;
const bool display_converted_string = false;
QElapsedTimer t;
std::cout << "Using clock type " << t.clockType() << ".\n";
QByteArray data(256, 0);
QByteArray newData;
qint64 elapsed1 = 0, elapsed2 = 0;
//Set the values in data to 0-255 to make sure all values are converted properly.
for(int i = 0; i < data.size(); ++i)
{
data[i] = i;
}
t.start();
for(int i = 0; i < iterations; ++i)
{
newData = foo1(data);
}
elapsed1 = t.nsecsElapsed();
std::cout << "foo1 elapsed time = " << elapsed1 << "\n";
if(display_converted_string)
{
std::cout << "newData = " << newData.data() << "\n";
}
t.restart();
for(int i = 0; i < iterations; ++i)
{
newData = foo2(data);
}
elapsed2 = t.nsecsElapsed();
std::cout << "foo2 elapsed time = " << elapsed2 << "\n";
if(display_converted_string)
{
std::cout << "newData = " << newData.data() << "\n";
}
return 0;
}
這個問題似乎是題外話題,因爲它是關於代碼審查。 – lpapp