| 原因 | 現象 | 排查方法 |
|---|---|---|
| 缺少結束符 \0 | 檔名後附帶隨機字元 | 檢視 CString::GetBuffer() 返回指標,strlen 實際長度是否超過邏輯長度 |
| 緩衝區長度不足 | 截斷或寫入越界 | CFileDialog 的 m_ofn.nMaxFile 預設 260 (MAX_PATH),長路徑需手動擴大 |
| Unicode/ANSI 混用 | 中文檔名亂碼 | 專案屬性 → 字元集:Unicode 統一;CString 內部為 wchar_t,GetBuffer 返回 LPWSTR |
CFileDialog dlg(FALSE, _T("txt"), _T("默認檔名.txt"),
OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT,
_T("文字檔 (*.txt)|*.txt|所有檔 (*.*)|*.*||"));
// 擴大緩衝區支援長路徑 (Windows 10 1607+ 支援長路徑)
dlg.m_ofn.nMaxFile = 32768; // 32K
TCHAR* bigBuf = new TCHAR[dlg.m_ofn.nMaxFile];
dlg.m_ofn.lpstrFile = bigBuf;
dlg.m_ofn.lpstrFile[0] = _T('\0');
if (dlg.DoModal() == IDOK) {
CString fileName = dlg.GetPathName(); // 自動處理 \0
// 存檔邏輯...
}
delete[] bigBuf;
GetPathName() 而非 GetFileName():前者含完整路徑,後者僅檔名,存檔需完整路徑。<longPathAware>true</longPathAware> (Win10 1607+),並擴大 nMaxFile。\ / : * ? " < > | 等非法字元。CString 檔名亂碼 90% 因**缺 \0、緩衝區太小、編碼不統一**。統一 Unicode、擴大 nMaxFile、用 GetPathName()、檢查結束符,即可徹底解決。