TL;DR — 依用途選方法的快速對照
- 立刻要轉、不想安裝任何東西 → FormatArc CSV 轉 JSON(瀏覽器內完成、不需上傳、支援 UTF-8 / 引號 / 欄位內換行)
- shell 腳本或單行指令 →
csvjson data.csv(csvkit)或mlr --icsv --ojson cat data.csv(Miller) - Python 專案內使用 →
csv.DictReader(標準函式庫、零外部依賴)或大型檔案用pandas.read_csv - Node.js 專案內使用 → PapaParse 的
{ header: true, dynamicTyping: true } - Go 微服務內使用 →
encoding/csv+ 表頭轉 map 的迴圈 - 記憶體放不下的大型檔案 →
csv.DictReader逐行輸出 NDJSON。禁止用json.dump一次輸出整個陣列
| 方法 | 安裝設定 | 大型檔案處理 | 型別推論 | NDJSON 輸出 |
|---|---|---|---|---|
| FormatArc 瀏覽器 | 無 | 有限制(整件讀入、受瀏覽器可用記憶體限制) | 無(全部保留為字串) | 無(建議用 CLI) |
Python csv.DictReader | 標準函式庫 | 可以(手寫迴圈) | 無(全部字串) | 可以 |
pandas read_csv | pip install pandas | 用 chunksize= 分塊串流 | 有(dtype 自動推論) | 可以(lines=True) |
Miller(mlr) | brew install miller | 可以(完整串流) | 有(--inumeric) | 可以(--ojsonl) |
csvkit(csvjson) | pip install csvkit | 有限制(整件讀入) | 有(--no-inference 可關閉) | 可以(--stream) |
| PapaParse(Node.js) | npm install papaparse | 可以(step 回呼串流) | 有(dynamicTyping) | 可以(手動串流) |
Go encoding/csv | 標準函式庫 | 可以(Read() 迴圈串流) | 無(手動轉換) | 可以(手動撰寫) |
本文逐一展示各方法的實際可執行程式碼,並針對實務中最常遇到的 4 個難點(輸出格式、編碼不一致、型別推論的陷阱、大型檔案效能最佳化)搭配具體案例說明。
CSV 格式基礎(RFC 4180)
CSV(Comma-Separated Values)是 RFC 4180在新分頁中開啟 中非正式規定的文字表格格式,但實務上存在各種方言。典型的 CSV 長這樣:
name,email,department,start_date
Alice Johnson,alice@example.com,Engineering,2024-01-15
Bob Smith,bob@example.com,Marketing,2023-06-01
Carol Williams,carol@example.com,Engineering,2024-03-10
第 1 行是表頭(欄位名稱),第 2 行起是資料記錄。欄位以逗號分隔,但外觀簡單不代表沒有坑:
- 含逗號的欄位必須用雙引號包起來:
"Smith, John" - 含雙引號的欄位用兩個連續雙引號轉義:
"She said ""hello""" - 引號內的換行是合法的(最常被簡易解析器搞壞的地方)
- 編碼沒有統一標準。UTF-8、UTF-8 BOM、Big5、Shift-JIS、Latin-1 等,視產出環境而定(Windows 版 Excel 預設輸出 UTF-8 帶 BOM 或 Big5)
- 分隔符號也未統一。TSV 用 Tab,歐洲地區 Excel 用分號(
;),部分資料集用直線(|)
CSV 的歷史與規範細節可參閱 RFC 4180 原文。
為什麼要把 CSV 轉成 JSON
實務上常遇到的需求:
- REST API 通訊:大多數現代的 Web API 要求 request body 是 JSON。用試算表管理的資料要 POST 到 API,就得先轉成 JSON 結構。
- 前端框架整合:React、Vue、Svelte、Next.js 等框架原生處理 JSON 物件與陣列。在瀏覽器端直接解析 CSV 也可以,但會增加不必要的 bundle 大小與解析開銷。
- 型別資訊保留:CSV 所有欄位都是文字(string)。JSON 可以明確區分 number、boolean、string、null。
- NoSQL 資料庫匯入:MongoDB(
mongoimport)、CouchDB、DynamoDB 的批次匯入工具直接讀取 JSON Lines(NDJSON)格式。 - 資料管線與工作流:Apache Airflow、Prefect、Mage、dbt 等資料處理工具在步驟間交換資料時常要求 JSON / NDJSON。
- LLM 上下文傳遞:把表格資料傳給 LLM 時,JSON 物件的明確鍵值結構比裸 CSV 更容易讓模型正確識別欄位,減少幻覺(hallucination)。
兩種格式的差異與資料模型,可以在 JSON 相關技術文件中找到完整說明。
5 種 JSON 輸出格式
大多數 CSV 轉 JSON 工具只提供一種格式:「以表頭為鍵的物件陣列」。但這不是所有場景都適用。同一份 CSV 可以轉出 5 種截然不同的 JSON 結構:
輸入 CSV:
id,name,score
1,Alice,95
2,Bob,87
3,Carol,92
輸出格式應該依據「接收端系統期望什麼」來決定,而不是跟着轉換工具的預設走:
| 格式 | JSON 結構 | 適用場景 | 產生方式 |
|---|---|---|---|
| 物件陣列 | [{...}, {...}] | REST API 或前端元件逐行接收 | 大多數轉換工具的預設 |
| Keyed 物件 | {"id": {...}} | 不需要逐行遍歷、想直接用 ID 查表 | Python 字典推導式 |
| JSON Lines(NDJSON) | 每行一個物件,不用陣列包 | 檔案大到記憶體放不下、或資料倉儲批次匯入 | 大型檔案用 mlr --ojsonl,記憶體中已有陣列時用 jq -c '.[]' |
| 欄位導向 | {"col": [v1, v2]} | 接收端 Python 程式期望每個欄位一個列表 | df.to_dict(orient="list") |
| 巢狀結構 | [{"a": {"b": v}}] | API 要求巢狀物件結構 | 以斜線(/)分隔的表頭 + 後處理 |
格式 1:物件陣列(大多數工具的預設)
[
{ "id": 1, "name": "Alice", "score": 95 },
{ "id": 2, "name": "Bob", "score": 87 },
{ "id": 3, "name": "Carol", "score": 92 }
]
用途:REST API 請求、前端資料渲染、一般資料交換。
格式 2:Keyed 物件(指定某欄位為主鍵)
{
"1": { "name": "Alice", "score": 95 },
"2": { "name": "Bob", "score": 87 },
"3": { "name": "Carol", "score": 92 }
}
用途:查表、以 ID 做 O(1) 字典取用。Python 產生方式:
import csv, json, sys
rows = list(csv.DictReader(sys.stdin))
result = {row["id"]: {k: v for k, v in row.items() if k != "id"} for row in rows}
json.dump(result, sys.stdout, indent=2, ensure_ascii=False)
格式 3:JSON Lines / NDJSON(換行分隔 JSON)
{"id":1,"name":"Alice","score":95}
{"id":2,"name":"Bob","score":87}
{"id":3,"name":"Carol","score":92}
用途:串流匯入(BigQuery、Snowflake COPY INTO、MongoDB mongoimport --type=json、日誌管線、Kafka producer)。每行都是完整的獨立 JSON 物件,所以 GB 級的檔案也能逐行處理而不必全部載入記憶體。
產生方式:Miller 的 mlr --icsv --ojsonl cat data.csv 或 jq -c '.[]' array.json > lines.ndjson。
格式 4:欄位導向(平行陣列)
{
"id": [1, 2, 3],
"name": ["Alice", "Bob", "Carol"],
"score": [95, 87, 92]
}
用途:資料科學(與 Apache Arrow / pandas 內部記憶體佈局一致)、GPU 加速管線、欄式資料庫。pandas 產生:df.to_dict(orient="list")。
格式 5:斜線分隔表頭產生巢狀結構
輸入 CSV(表頭用斜線表示層級):
id,name,address/city,address/zip
1,Alice,Taipei,10048
2,Bob,Kaohsiung,80047
輸出(巢狀 JSON):
[
{ "id": 1, "name": "Alice", "address": { "city": "Taipei", "zip": "10048" } },
{ "id": 2, "name": "Bob", "address": { "city": "Kaohsiung", "zip": "80047" } }
]
用途:產生要求巢狀結構的 API 請求 body。大多數轉換工具需要額外後處理。
方法 1:FormatArc 瀏覽器工具(不需上傳)
現在就要轉、又不想裝任何軟體的話,FormatArc CSV 轉 JSON 是最快的選擇。所有運算都在瀏覽器內完成,資料不會傳到任何外部伺服器。
- 打開 CSV 轉 JSON 轉換器
- 把 CSV 文字貼到左側編輯器
- 點「轉換」按鈕,右側出現整理好的 JSON 結果


簡易解析器常出錯的邊界狀況也能正確處理:引號欄位內的逗號、含換行的儲存格、空欄位(轉為空字串)等。
瀏覽器內處理在處理敏感資料時特別重要。客戶個資、薪資資料、從 vault 匯出的 API key、公司內部財務指標——貼上去的資料只存在目前的瀏覽器分頁中,沒有任何上傳或伺服器端處理。
方法 2:Python — csv.DictReader 與 pandas
Python 標準函式庫內建 csv 與 json 模組,基本轉換不需要安裝任何第三方套件:
import csv
import json
import sys
reader = csv.DictReader(sys.stdin)
rows = list(reader)
json.dump(rows, sys.stdout, indent=2, ensure_ascii=False)
存成 csv2json.py 後執行:
python3 csv2json.py < data.csv > data.json
csv.DictReader 會自動把第 1 行當表頭。每行變成一個 dict,dict 的列表直接對應 JSON 的物件陣列。ensure_ascii=False 在 CSV 含有中文、日文字母、特殊符號時很重要,漏掉的話中文字會被轉成 \uXXXX Unicode 逸出序列。
使用 pandas(大型檔案 + 型別推論)
資料分析環境或大型檔案處理用 pandas 比較方便:
import pandas as pd
df = pd.read_csv("data.csv", encoding="utf-8")
df.to_json("data.json", orient="records", indent=2, force_ascii=False)
orient="records" 輸出物件陣列。其他選擇有 "index"(Keyed 物件)、"columns"(欄位導向)、"values"(陣列的陣列)。
記憶體放不下的檔案用 chunksize 串流處理:
import pandas as pd
with open("output.ndjson", "w", encoding="utf-8") as out:
for chunk in pd.read_csv("huge.csv", chunksize=10000):
chunk.to_json(out, orient="records", lines=True, force_ascii=False)
out.write("\n")
以 NDJSON 格式輸出,記憶體中任何時刻只保持 10000 行,所以可以用恆定的記憶體用量處理任意大小的檔案。
方法 3:Node.js — PapaParse
JavaScript 與 Node.js 生態中解析 CSV 的事實標準是 papaparse。FormatArc 的瀏覽器工具內部也使用 PapaParse。
const Papa = require("papaparse");
const fs = require("fs");
const csv = fs.readFileSync("data.csv", "utf8");
const result = Papa.parse(csv, {
header: true,
dynamicTyping: true, // "42" → 42, "true" → true
skipEmptyLines: true,
});
fs.writeFileSync("data.json", JSON.stringify(result.data, null, 2));
GB 級大型檔案用 Node.js 串流搭配 step 回呼,把記憶體用量降到最低:
const fs = require("fs");
const Papa = require("papaparse");
const stream = fs.createReadStream("huge.csv");
const out = fs.createWriteStream("huge.ndjson");
Papa.parse(stream, {
header: true,
dynamicTyping: true,
step: (row) => out.write(JSON.stringify(row.data) + "\n"),
complete: () => out.end(),
});
每行立刻寫入磁碟,不管檔案多大使記憶體用量保持恆定。
方法 4:Go — encoding/csv
Go 標準函式庫的 encoding/csv 與 encoding/json 搭配即可達成高效能轉換:
package main
import (
"encoding/csv"
"encoding/json"
"fmt"
"os"
)
func main() {
f, err := os.Open("data.csv")
if err != nil {
panic(err)
}
defer f.Close()
reader := csv.NewReader(f)
records, err := reader.ReadAll()
if err != nil {
panic(err)
}
headers := records[0]
result := make([]map[string]string, 0, len(records)-1)
for _, row := range records[1:] {
obj := make(map[string]string, len(headers))
for i, val := range row {
obj[headers[i]] = val
}
result = append(result, obj)
}
out, _ := json.MarshalIndent(result, "", " ")
fmt.Println(string(out))
}
Go 的 encoding/csv 預設把所有欄位當作字串處理。如果要轉成數值或布林型別,需要手動呼叫 strconv.Atoi、strconv.ParseFloat、strconv.ParseBool。
處理大型檔案時,把 ReadAll() 改成 for 迴圈中的 Read(),逐行讀取並用 json.Marshal 寫入 NDJSON 檔案,就能控制記憶體在恆定水平。
方法 5:Miller 與 csvkit(單行 CLI)
在終端機或 shell 腳本中想要一鍵完成轉換時,這兩個 CLI 工具非常實好用。
Miller(mlr)
Miller 是針對結構化資料的高效能串流處理器,地位類似結構化資料領域的 awk:
# 轉成 JSON 物件陣列
mlr --icsv --ojson cat data.csv > data.json
# NDJSON(適合串流管線)
mlr --icsv --ojsonl cat data.csv > data.ndjson
# 轉換同時做過濾
mlr --icsv --ojson filter '$score > 90' data.csv
# 轉換時新增計算欄位
mlr --icsv --ojson put '$grade = $score >= 90 ? "A" : "B"' data.csv
安裝:macOS 用 brew install miller,Linux(Debian/Ubuntu)用 apt install miller。
csvkit(csvjson)
csvkit 是 Python 系的 CSV 工具套件:
pip install csvkit
csvjson data.csv > data.json
常用選項:
--indent 2— 帶縮排的整潔 JSON 輸出--no-inference— 關閉自動數值轉換,全部保留為字串--stream— 不用陣列包,改以 NDJSON 串流輸出--locale zh_TW.UTF-8— 依地區格式解析數值
只是想快速在終端機拿到 NDJSON,csvjson --stream 是最省事的選擇。
巢狀 JSON 產生(斜線分隔表頭)
大多數轉換器只回傳一維的扁平物件。如果下游的 REST API、MongoDB schema、GraphQL resolver 需要巢狀結構,就需要後處理邏輯。
實務上有一種常見慣例:在表頭中用斜線(/)或句點(.)表示層級:
id,name,address/city,address/zip,address/country
1,Alice,Taipei,10048,TW
2,Bob,Kaohsiung,80047,TW
Python 產生巢狀物件:
import csv, json, sys
def nest(row, sep="/"):
result = {}
for key, val in row.items():
parts = key.split(sep)
cursor = result
for part in parts[:-1]:
cursor = cursor.setdefault(part, {})
cursor[parts[-1]] = val
return result
reader = csv.DictReader(sys.stdin)
rows = [nest(r) for r in reader]
json.dump(rows, sys.stdout, indent=2, ensure_ascii=False)
輸出結果:
[
{ "id": "1", "name": "Alice", "address": { "city": "Taipei", "zip": "10048", "country": "TW" } },
{ "id": "2", "name": "Bob", "address": { "city": "Kaohsiung", "zip": "80047", "country": "TW" } }
]
如果想用句點記法(address.city),把 sep="." 傳入即可。
編碼與語法問題(Big5 / UTF-8 BOM / 引號逗號 / 內嵌換行)
編碼不一致是 CSV 轉 JSON 時文字變亂碼的最主要原因。
Big5 與 Big5-ETC(繁體中文 Excel 預設編碼)
繁體中文 Windows 版 Excel 在「另存新檔」選「CSV(以逗號分隔)」時,預設使用 Big5 編碼而非 UTF-8。把 Big5 檔案當成 UTF-8 讀取會產生亂碼,例如「姓名」變成「åå'»åå'§」之類的無意義字元。
這是繁體中文開發者最常遇到的編碼問題,也是和日韓環境最大的差異所在:日版 Excel 預設 Shift-JIS,韓版預設 CP949/EUC-KR,但繁中環境預設 Big5。
Python 中指定 Big5 讀取:
with open("data.csv", encoding="big5") as f:
reader = csv.DictReader(f)
如果檔案實際上是 Big5-ETC(Big5 的扩展版,多了一些罕用字),用:
with open("data.csv", encoding="big5") as f:
# 或 encoding="big5hk" 視環境而定
reader = csv.DictReader(f)
終端機中一併轉成 UTF-8:
iconv -f BIG5 -t UTF-8 data.csv > data.utf8.csv
如果是 Big5-ETC 的檔案:
iconv -f BIG5-ETC -t UTF-8 data.csv > data.utf8.csv
FormatArc 瀏覽器工具 以 UTF-8 輸入為標準。Big5 檔案請先用 iconv 或在文字編輯器中「另存新檔」選 UTF-8 編碼,再貼上內容。
UTF-8 BOM(Byte Order Mark)
Windows 版 Excel 選「CSV UTF-8」格式儲存時,檔案開頭會多 3 位元組的 BOM(EF BB BF)。多數 JSON 解析器不會自動去除 BOM,導致第一個欄位的鍵名變成 name 前面帶了看不見字元的 name。
Python 去除 BOM:
with open("data.csv", encoding="utf-8-sig") as f:
# -sig 選項會自動去除 BOM
reader = csv.DictReader(f)
Miller 去除 BOM:mlr --icsv --ojson cat <(sed '1s/^\xEF\xBB\xBF//' data.csv)。
Latin-1(歐洲版 Excel 預設)
歐洲地區 Excel 常以 Latin-1(Windows-1252)儲存。處理方式與 Big5 類似:iconv -f LATIN1 -t UTF-8 或在 Python 中指定 encoding="latin-1"。
引號內的逗號與儲存格內換行
含分隔符號(逗號)或換行符號的欄位必須用引號包起來:
id,description
1,"Hello, world"
2,"Multi-line
description here"
用 string.split(",") 這種簡易實作會把第 1 行的逗號當成欄位邊界、把第 2 行的換行當成記錄結束,完全解析錯誤。務必使用符合 RFC 4180 規範的正式 CSV 解析器(csv.DictReader、PapaParse、Miller、csvkit)。
逗號以外的分隔符號(分號 / Tab / 直線)
歐洲地區 Excel 用分號(;)做欄位分隔(因為小數點用逗號表示)。這時要明確指定分隔符號:
reader = csv.DictReader(f, delimiter=";")
mlr --csv --ifs ";" --ojson cat data.csv
Papa.parse(csv, { header: true, delimiter: ";" });
TSV(Tab 分隔)用 delimiter="\t" 或 Miller 的 --itsv 選項。
型別推論(數值 / 布林 / null 的解釋)
CSV 本質上所有值都是文字。轉成 JSON 時要不要自動轉成數值或布林,各工具行為不同:
| 工具 | 預設行為 | 啟用型別推論 |
|---|---|---|
Python csv.DictReader | 全部字串 | 手動轉換(casting) |
pandas read_csv | 逐欄自動推論 | 預設開啟,dtype=str 可關閉 |
| PapaParse(Node.js) | 全部字串 | { dynamicTyping: true } |
Miller(mlr) | 全部字串 | --inumeric 旗標 |
csvkit(csvjson) | 自動推論開啟 | --no-inference 可關閉 |
| FormatArc 瀏覽器 | 全部保留為字串(防止資料失真) | 無 |
不小心開啟自動型別推論時的危險:
"007"被轉成數字7,前導零消失(電話號碼、郵政編號、員工編號、ISBN 會造成嚴重問題)"NaN"、"Infinity"字串被轉成浮點數值"true"、"false"、"yes"、"no"被自動轉成布林值- 空字串
""視工具不同被轉成null、保留為""、或整個欄位被省略 - 超過 15 位的數字型 ID 會被 JavaScript 雙精確度浮點數上限(
Number.MAX_SAFE_INTEGER=2^53 - 1)截斷尾數
安全原則:生產環境的資料管線中,全部欄位保留為字串輸出,在明確知道 schema 的應用層再做型別轉換。自動推論在分析場景很方便,但在正式管線中不穩定。
效能與大型檔案
幾 MB 以內的小檔案,用哪種方法速度差不到有感。差距開始出現是在資料量超出記憶體舒適範圍的時候。
| 檔案規模 | 建議方法 | 理由 |
|---|---|---|
| 記憶體放得下 | FormatArc 瀏覽器 / csvkit / pandas | 不需要串流,快速完成 |
| 一次載入太吃緊 | pandas chunksize / Miller / PapaParse stream / Go | 逐行或分塊處理,避免 OOM |
| 非常大(數 GB 以上) | Miller / Go encoding/csv / Python csv.DictReader + NDJSON | 必須恆定記憶體的純串流 |
吞吐量實測(Apple M5 Pro / 64GB RAM / macOS 26.5、5 欄 1,000,000 行 CSV、單執行緒,重現腳本見 scripts/benchmarks/csv-to-json-throughput/):
- Python
csv.DictReader+json.dump(Python 3.14.6):約 232,000 行/秒 - pandas
read_csv+to_json(pandas 3.0.3):約 1,113,000 行/秒 - Miller
mlr --c2j(Miller 6.19.0):約 1,960,000 行/秒(5 次量測的暖機中位數;冷機首次因 FS cache 未命中約 990,000 行/秒) - Go
encoding/csv+encoding/json(Go 1.26.4):約 2,058,000 行/秒 - PapaParse streaming(papaparse 5.5.2 / Node 26.3.1):約 1,626,000 行/秒
- FormatArc 瀏覽器工具:內部使用 PapaParse 5.5 引擎,但受瀏覽器主執行緒響應度與分頁記憶體上限制約,吞吐量不及 CLI 工具。實務上數十 MB、數十萬行是舒適的操作範圍。
以上數值隨硬體、OS、工具版本差異很大。舊款 CPU 或舊版套件(pandas 2.x、Miller 5.x)會明顯偏低。重要系統請在自己的環境重測。
TB 級大資料已經超出這些單機工具的適用範圍,應改用 DuckDB(COPY data FROM 'data.csv' (FORMAT CSV) → COPY (SELECT * FROM data) TO 'out.ndjson' (FORMAT JSON, ARRAY false))、Apache Spark、Apache Arrow。
任意大小檔案的串流模式(Python)
import csv
import json
import sys
writer = sys.stdout
reader = csv.DictReader(open("huge.csv", encoding="utf-8"))
for row in reader:
writer.write(json.dumps(row, ensure_ascii=False) + "\n")
以 NDJSON 格式逐行即時輸出。每行只消耗一行的記憶體,不隨輸入大小增加。可透過 pipe 用 gzip -c > out.ndjson.gz 即時壓縮,或直接串流到 BigQuery、AWS S3。
CI/CD 工作流(curl POST 與 GitHub Actions)
實務上常見的需求:Git 倉庫中管理的 CSV 檔,每次 push 都自動轉 JSON 並 POST 到 API。
# 執行轉換
python3 csv2json.py < users.csv > users.json
# POST 到 API
curl -X POST https://api.example.com/users/bulk \
-H "Content-Type: application/json" \
-H "Authorization: Bearer $API_TOKEN" \
-d @users.json
GitHub Actions 工作流:
name: Sync user CSV to API
on:
push:
paths: ["data/users.csv"]
jobs:
sync:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Install Miller
run: sudo apt-get install -y miller
- name: Convert and upload
env:
API_TOKEN: ${{ secrets.API_TOKEN }}
run: |
mlr --icsv --ojson cat data/users.csv > users.json
curl -fsS -X POST https://api.example.com/users/bulk \
-H "Content-Type: application/json" \
-H "Authorization: Bearer $API_TOKEN" \
-d @users.json
如果只是要快速測試 API,把 CSV 貼到 CSV 轉 JSON 工具 中,複製產生的 JSON 到 Postman、Insomnia 或 curl 就夠了。
常見問題
Excel 輸出的 CSV 帶 BOM,FormatArc 能處理嗎?
可以。FormatArc 瀏覽器工具 會自動偵測並去除 UTF-8 BOM。Python 端用 encoding="utf-8-sig",Node.js 的 PapaParse 也會透明處理 BOM。
能輸出 NDJSON(JSON Lines)嗎?
目前 FormatArc 瀏覽器工具輸出標準 JSON 陣列。如果需要 NDJSON,用 Miller(mlr --icsv --ojsonl)或 csvkit(csvjson --stream)。日誌管線和資料庫批次匯入都以此格式為標準。
沒有表頭的 CSV 怎麼轉?
Python csv.DictReader 用 fieldnames 參數手動指定欄位名:
reader = csv.DictReader(f, fieldnames=["id", "name", "score"])
PapaParse 用 Papa.parse(csv, { header: false }) 取得二維陣列(陣列的陣列),再手動映射成物件。
數字 ID 欄被輸出成字串怎麼辦?
大多數工具預設全部輸出字串以防止資料失真。要輸出數字就開啟型別推論:PapaParse 的 dynamicTyping: true、Miller 的 --inumeric、pandas 的 dtype。但超過 15 位的 ID 會受 JavaScript 雙精確度浮點數上限影響而失去尾數精度。
JSON 鍵名開頭看到  字元?
這是 UTF-8 BOM 被當成 Latin-1 解碼後顯示的結果。Python 讀取時指定 encoding="utf-8-sig",或用 sed '1s/^\xEF\xBB\xBF//' data.csv 先去除 BOM。
瀏覽器能轉的最大 CSV 大小是多少?
沒有固定上限,取決於你的裝置與瀏覽器分頁可用記憶體。瀏覽器同時持有原始文字與解析後的 JSON 物件,所以實際記憶體使用會超過檔案本身的大小。GB 級大型檔案建議用 Miller、pandas chunksize、或 Go 串流程式處理。
CSV 儲存格內含 JSON 字串怎麼轉?
儲存格內有 "{""key"":""value""}" 這種 JSON 字串時,先以文字解析 CSV,再對該欄位套用 json.loads():
import pandas as pd, json
df = pd.read_csv("data.csv")
df["metadata"] = df["metadata"].apply(json.loads)
df.to_json("data.json", orient="records", force_ascii=False)
JSON 輸出能保持欄位順序嗎?
主流工具都保留欄位順序。Python 3.7 以上的 dict 維持插入順序,csv.DictReader 依表頭順序,pandas to_json(orient="records") 也維持欄位順序。json.dump 在沒傳 sort_keys=True 時不會重新排序。
相關工具
- CSV 轉 JSON 轉換器 — 瀏覽器內即時轉換,不需上傳到伺服器
- JSON 轉 YAML 轉換器 — 將產生的 JSON 轉為 Kubernetes、Docker Compose、OpenAPI 規格用的 YAML
- JSON 格式化器 — JSON 資料縮排整理與語法錯誤檢查
- CSV 轉 Markdown 轉換器 — 把試算表或 CSV 資料轉成 GitHub 相容的 Markdown 表格
總結
CSV 轉 JSON 的方法很多,依用途選對工具才是關鍵:
- 不需安裝、處理機敏資料:FormatArc CSV 轉 JSON — 瀏覽器內完成、無上傳、處理編碼問題
- Shell 管線與 CLI 自動化:Miller(
mlr --icsv --ojson)或 csvkit(csvjson) - Python 專案:標準函式庫
csv.DictReader,大型檔案與型別推論用 pandas - Node.js 專案:PapaParse(
dynamicTyping與大型檔案的step串流) - Go 微服務:
encoding/csv+ 逐行串流迴圈
四個關鍵要點:選對輸出格式(陣列 / NDJSON / Keyed / 欄位導向 / 巢狀)、確認輸入檔案編碼(Big5 / UTF-8 BOM / Latin-1)、決定要不要型別推論、記憶體放不下的檔案改用串流處理。