從 Windows 移植代碼到 Linux 時,常遇到 std::to_string() 在舊版 GCC(< 4.9)或嚴格標準模式下不可用的問題。本文推薦使用 std::stringstream 實現通用、高效的數值轉字符串,並提供即插即用的封裝函數。
C++11 引入 std::to_string,但早期 GCC 版本(如 4.8)未完整實現,或需 -std=c++11 且定義 _GLIBCXX_USE_CXX11_ABI。為保證跨平台兼容性,手寫一個 to_string 替代品是穩妥選擇。
#include <iostream>
#include <sstream>
#include <string>
using namespace std;
string to_string(int value) {
ostringstream oss;
oss << value;
return oss.str();
}
// 通用模板版本(支持所有流輸出類型)
template <typename T>
string to_string(T value) {
ostringstream oss;
oss << value;
return oss.str();
}
int main() {
int n = 10;
cout << to_string(n) << endl; // "10"
cout << to_string(3.14) << endl; // "3.14"
cout << to_string(123456789L) << endl; // "123456789"
return 0;
}
| 方法 | 優點 | 缺點 |
|---|---|---|
sprintf/snprintf | C 風格,高性能 | 需手動管理緩衝區,類型不安全 |
std::to_string (C++11) | 標準、簡潔 | 舊編譯器不支持 |
boost::lexical_cast | 功能強大 | 引入重型依賴 |
stringstream | 標準庫、類型安全、可擴展、無額外依賴 | 較 sprintf 略慢(可忽略) |
若極度追求性能(如高頻日誌),可使用 fmt 庫(C++20 std::format 前身)或手寫整數轉換:
// 僅供參考:手寫 int→string(無分配,極快)
string int_to_string(int x) {
if (x == 0) return "0";
bool neg = x < 0; if (neg) x = -x;
char buf[12]; int i = 11;
while (x) { buf[i--] = '0' + x % 10; x /= 10; }
if (neg) buf[i--] = '-';
return string(buf + i + 1, 11 - i);
}
在 Linux 移植項目中,添加一個基於 stringstream 的 to_string 重載,即可無縫替換標準庫版本,兼容性最佳,代碼侵入性最小。建議放在公共頭文件中,全項目統一使用。