早期 MIS 系統多基於 FoxPro 2.x (DBF) 構建,升級 Oracle 時需將海量 DBF 匯入。手工編寫 CREATE TABLE 與 SQL*Loader 控制檔(.ctl)不僅繁瑣,且極易在 POSITION 起止位置上出錯,嚴重拖慢遷移進度。
load.cpp 設計輸入:FoxPro 資料庫名(或目錄)。
輸出三類文件:
CREATE TABLE,類型映射規則:
VARCHAR2(n)NUMBER(p,s)(注意 FoxPro 寬度含小數點,Oracle 不含)CHAR(1)(Oracle 無布林型)DATEPOSITION(start:end),生成 INFILE、FIELDS TERMINATED BY 等子句。// 伪代碼示意
void GenerateAll(const char* dbName) {
DBFHeader hdr = ReadHeader(dbName);
vector fields = ReadFields(dbName);
// 1. 導出 SDF 數據
ExportSDF(dbName, fields, "data.txt");
// 2. 生成 CREATE TABLE
ofstream sql("create.sql");
sql << "CREATE TABLE " << dbName << " (\n";
for (auto& f : fields) {
sql << " " << f.name << " " << MapType(f) << ",\n";
}
sql.seekp(-2, ios::cur); // 移除最後逗號
sql << "\n);\n";
// 3. 生成 .ctl
ofstream ctl("load.ctl");
ctl << "LOAD DATA\n"
<< "INFILE 'data.txt'\n"
<< "INTO TABLE " << dbName << "\n"
<< "FIELDS FIXED\n"
<< "(\n";
int pos = 1;
for (auto& f : fields) {
ctl << " " << f.name << " POSITION(" << pos << ":" << pos+f.len-1 << ")"
<< (f.type=='N' ? " EXTERNAL" : "") << ",\n";
pos += f.len;
}
ctl.seekp(-2, ios::cur);
ctl << "\n)\n";
}
POSITION 手算錯誤,數據加載零失敗。結合 Oracle EXTERNAL TABLE、Data Pump 或 Python cx_Oracle 進一步實現全自動化 ETL 流水線。