गाइड

Python में JSON: फ़ाइलें पढ़ना और लिखना, CSV, pathlib और UTF-8 एन्कोडिंग

अपडेट किया गया: · Skillaria.Top

Python में JSON के लिए स्टैंडर्ड मॉड्यूल json है: json.load फ़ाइल से डेटा पढ़ता है, json.dump फ़ाइल में लिखता है, और json.loads व json.dumps यही काम स्ट्रिंग के साथ करते हैं। फ़ाइल को with open(path, encoding="utf-8") से खोलें, पथ pathlib.Path से बनाएँ, और सारणी (टेबल) वाला डेटा csv मॉड्यूल से पढ़ें।

Python में JSON के साथ काम करने के लिए किसी बाहरी लाइब्रेरी की ज़रूरत नहीं: मॉड्यूल json स्टैंडर्ड लाइब्रेरी में है, और डिक्शनरी व लिस्ट को टेक्स्ट में और वापस बदलता है। इसके साथ लगभग हमेशा तीन चीज़ें और चाहिए होती हैं: with के साथ open फ़ंक्शन, पथों के लिए pathlib, और सारणी के लिए csv मॉड्यूल। नीचे सब कुछ क्रम से है, चलने वाले कोड और उन गड्ढों के साथ जिनमें लोग सबसे ज़्यादा गिरते हैं।

Python में open फ़ंक्शन: मोड और एन्कोडिंग

कोई भी टेक्स्ट फ़ाइल बिल्ट-इन फ़ंक्शन open(path, mode, encoding=...) से खुलती है। वह एक फ़ाइल ऑब्जेक्ट लौटाता है, जिसमें read, readline, write मेथड होते हैं और जिस पर लूप पंक्ति-दर-पंक्ति चलाया जा सकता है।

मोडक्या करता है
"r"पढ़ना (डिफ़ॉल्ट)। फ़ाइल न हो तो FileNotFoundError
"w"लिखना। फ़ाइल बनती है या खुलते ही खाली हो जाती है
"a"अंत में जोड़ना, पुराना कंटेंट वैसा ही रहता है
"x"नई फ़ाइल बनाना; पहले से हो तो FileExistsError
"b"मोड में जोड़ा जाता है: बाइट्स के साथ काम ("rb", "wb")

with क्यों ज़रूरी है

फ़ाइल को बंद करना ज़रूरी है: वरना डेटा शायद डिस्क पर न पहुँचे, और सिस्टम डिस्क्रिप्टर अटका रहता है। with फ़ाइल को अपने-आप बंद करता है — ब्लॉक के भीतर एरर आने पर भी।

with open("notes.txt", "w", encoding="utf-8") as f:
    f.write("पहली पंक्ति\n")
    f.write("दूसरी पंक्ति\n")

with open("notes.txt", encoding="utf-8") as f:
    for line in f:
        print(line.rstrip("\n"))

फ़ाइल पर लूप चलाने से वह एक-एक पंक्ति पढ़ी जाती है और पूरी मेमोरी में नहीं आती, इसलिए गीगाबाइट वाले लॉग भी इसी तरह संसाधित हो सकते हैं। f.read() पूरा कंटेंट एक स्ट्रिंग में देता है, और f.readlines() पंक्तियों की सूची।

फ़ाइल में स्ट्रिंग जोड़ना, पुराना न मिटाना

सबसे आम गलती: कुछ «जोड़ने» के लिए फ़ाइल को "w" मोड में खोल देना। मोड "w" खोलते ही फ़ाइल को खाली कर देता है, पहले write से पहले ही। अंत में जोड़ने के लिए "a" लें, और किसी मौजूदा फ़ाइल को गलती से न बदलने के लिए "x"।

with open("log.txt", "a", encoding="utf-8") as f:
    f.write("नई प्रविष्टि\n")

ध्यान रहे, write ख़ुद नई पंक्ति नहीं जोड़ता — "\n" साफ़ लिखना होता है। या print(..., file=f) इस्तेमाल करें, वह लाइन-ब्रेक अपने-आप लगा देता है।

UTF-8 एन्कोडिंग: «क्रैक्षोज़ब्रा» कहाँ से आते हैं

Python 3.15 से पहले open() में encoding न हो, तो वह सिस्टम की एन्कोडिंग लेता था। Linux और macOS पर यह UTF-8 है, पर Windows पर हिंदी या रूसी लोकेल में cp1251 जैसी। एक स्क्रिप्ट जो सर्वर पर ठीक चलती थी, दूसरे कंप्यूटर पर «Р•РґР°» जैसा कूड़ा छापती थी, या UnicodeDecodeError देती थी।

Python 3.15 में PEP 686 के अनुसार UTF-8 मोड डिफ़ॉल्ट है: encoding के बिना भी open() हर OS पर UTF-8 में पढ़ता और लिखता है। पुराना व्यवहार वापस पाने के लिए एनवायरनमेंट वेरिएबल PYTHONUTF8=0 या फ़्लैग -X utf8=0 है, और सिस्टम की एन्कोडिंग साफ़ माँगने के लिए encoding="locale"।

import sys
print(sys.flags.utf8_mode)   # Python 3.15 में 1

open("legacy.txt", encoding="locale")   # सिस्टम की एन्कोडिंग
open("old_excel.csv", encoding="cp1251")  # cp1251 में सहेजी फ़ाइल

इसका दूसरा पहलू: Excel या Windows स्क्रिप्ट से cp1251 में सहेजी पुरानी CSV अब UTF-8 समझकर पढ़ी जाएगी और UnicodeDecodeError देगी। इलाज: उसे encoding="cp1251" से पढ़ें और UTF-8 में दोबारा सहेजें। अच्छी आदत नहीं बदलती — encoding हमेशा साफ़ लिखें, तब कोड हर वर्ज़न पर एक जैसा चलेगा।

Python में pathlib: पथ को ऑब्जेक्ट की तरह

पथों को स्ट्रिंग से जोड़ना ("data" + "/" + name) असुविधाजनक है और अलग-अलग OS पर टूटता है। मॉड्यूल pathlib में Path क्लास है, जहाँ पथ / ऑपरेटर से जुड़ते हैं, और ऑब्जेक्ट के पास साफ़ गुण होते हैं।

from pathlib import Path

data = Path("data")
csv_path = data / "expenses.csv"

print(csv_path.name)    # expenses.csv
print(csv_path.stem)    # expenses
print(csv_path.suffix)  # .csv
print(csv_path.parent)  # data
print(csv_path.exists())

data.mkdir(parents=True, exist_ok=True)
(data / "hello.txt").write_text("नमस्ते", encoding="utf-8")
print((data / "hello.txt").read_text(encoding="utf-8"))

for p in data.glob("*.csv"):
    print(p)

छोटी फ़ाइलों के लिए read_text और write_text open + with की जगह ले लेते हैं। Path ऑब्जेक्ट को साधारण open, json और csv — सभी स्वीकार करते हैं। स्क्रिप्ट की अपनी फ़ाइल के सापेक्ष पथ (मौजूदा फ़ोल्डर के सापेक्ष नहीं) के लिए लिखें: Path(__file__).parent / "data"।

Python 3.14 में Path पर copy() और move() मेथड आए, इसलिए साधारण कॉपी के लिए shutil की ज़रूरत नहीं रही। उसी वर्ज़न में स्टैंडर्ड लाइब्रेरी में Zstandard कंप्रेशन के लिए मॉड्यूल compression.zstd भी आया (PEP 784)।

Python में JSON: load, dump, loads, dumps

JSON डेटा के आदान-प्रदान का टेक्स्ट फ़ॉर्मैट है: API इसे भेजते हैं, कॉन्फ़िग और रिपोर्ट इसमें रखे जाते हैं। मॉड्यूल json दो काम करता है: सीरियलाइज़ेशन (Python ऑब्जेक्ट → JSON टेक्स्ट) और डीसीरियलाइज़ेशन (टेक्स्ट → ऑब्जेक्ट)। फ़ंक्शन चार हैं, और उनमें गड़बड़ी आम सवाल है।

फ़ंक्शनक्या करता है
json.dumps(obj)ऑब्जेक्ट → JSON स्ट्रिंग
json.loads(s)JSON स्ट्रिंग → ऑब्जेक्ट
json.dump(obj, f)ऑब्जेक्ट → खुली फ़ाइल में लिखना
json.load(f)खुली फ़ाइल से JSON पढ़ना

याद रखना आसान है: आख़िर का s string यानी स्ट्रिंग के लिए है; उसके बिना फ़ाइल के लिए।

टाइप का मिलान

PythonJSON
dictऑब्जेक्ट {}
list, tupleऐरे []
strस्ट्रिंग
int, floatसंख्या
True / Falsetrue / false
Nonenull

टपल वापस पढ़ने पर सूची बन जाएगा, और सेट, तारीख़ें या Decimal मॉड्यूल नहीं जानता — वह TypeError: Object of type ... is not JSON serializable देगा।

JSON फ़ाइल में सहेजना

import json
from pathlib import Path

report = {
    "month": "2026-10",
    "total": 15230.5,
    "categories": {"खाना": 8200, "यात्रा": 2100},
    "tags": ["घर", "काम"],
}

path = Path("data/report.json")
path.parent.mkdir(parents=True, exist_ok=True)
with path.open("w", encoding="utf-8") as f:
    json.dump(report, f, ensure_ascii=False, indent=2)

ensure_ascii=False हिंदी अक्षरों को जैसे हैं वैसे रखता है। इसके बिना फ़ाइल में «खाना» की जगह "खाना" जैसा कोड आएगा — वह सही JSON है, पर इंसान के लिए पढ़ना असंभव। indent=2 सुंदर इंडेंटेड फ़ॉर्मैट देता है।

JSON फ़ाइल से पढ़ना

with open("data/report.json", encoding="utf-8") as f:
    data = json.load(f)

print(data["total"])               # 15230.5
print(data["categories"]["खाना"])  # 8200

परिणाम एक साधारण डिक्शनरी या सूची है, जिसके साथ आप हमेशा की तरह काम करते हैं। अगर फ़ाइल JSON न हो या अधूरी हो, तो json.JSONDecodeError आएगा, जिसमें पंक्ति और स्थिति की जानकारी होती है — जब डेटा बाहर से आए, तो इसे पकड़ना चाहिए।

JSON स्ट्रिंग का पार्सिंग और सुंदर आउटपुट

import json

raw = '{"name": "अनीता", "skills": ["python", "sql"], "active": true}'
user = json.loads(raw)
print(user["skills"][0])   # python

print(json.dumps(user, ensure_ascii=False, indent=2, sort_keys=True))

sort_keys=True कुंजियों को क्रम में छापता है — git में फ़ाइलों की तुलना के लिए सुविधाजनक। टर्मिनल से फ़ाइल को सुंदर बनाने के लिए मॉड्यूल का अंतर्निहित टूल है: python -m json.tool data/report.json।

HTTP API का जवाब भी JSON स्ट्रिंग होता है। लाइब्रेरी requests उसे response.json() से पार्स करती है, और भीतर वही json.loads चलता है।

जाल: JSON की कुंजियाँ हमेशा स्ट्रिंग होती हैं

d = {1: "जनवरी", 2: "फ़रवरी"}
back = json.loads(json.dumps(d))
print(back == d)   # False
print(back)        # {'1': 'जनवरी', '2': 'फ़रवरी'}
# back[1] -> KeyError, इसके बजाय back["1"]

fixed = {int(k): v for k, v in back.items()}

JSON में ऑब्जेक्ट की कुंजियाँ सिर्फ़ स्ट्रिंग हो सकती हैं, इसलिए संख्यात्मक कुंजियाँ सीरियलाइज़ेशन के बाद स्ट्रिंग बन जाती हैं। पढ़ते समय उन्हें वापस बदलें।

अपने प्रकार: तारीख़ें और Decimal

import json
from datetime import date

def default(obj):
    if isinstance(obj, date):
        return obj.isoformat()
    raise TypeError(f"{type(obj).__name__} को सीरियलाइज़ नहीं कर सकते")

print(json.dumps({"day": date(2026, 10, 1)}, default=default))
# {"day": "2026-10-01"}

default पैरामीटर में दिया फ़ंक्शन हर अज्ञात ऑब्जेक्ट के लिए बुलाया जाता है। जटिल मामलों के लिए json.JSONEncoder से उत्तराधिकार लेकर उसका default मेथड बदला जा सकता है।

JSON ऐरे में एक तत्व जोड़ना

JSON को टेक्स्ट लॉग की तरह अंत में नहीं जोड़ा जा सकता: फ़ाइल को पढ़ना, बदलना और पूरा दोबारा लिखना होता है।

path = Path("data/items.json")
items = json.loads(path.read_text(encoding="utf-8")) if path.exists() else []
items.append({"id": len(items) + 1, "title": "नया"})
path.write_text(json.dumps(items, ensure_ascii=False, indent=2), encoding="utf-8")

अगर प्रविष्टियाँ बहुत हैं और लगातार जुड़ती हैं, तो JSON Lines फ़ॉर्मैट सुविधाजनक है: हर पंक्ति में एक JSON ऑब्जेक्ट, और फ़ाइल "a" मोड में खुलती है।

Python में CSV: csv मॉड्यूल

CSV टेक्स्ट फ़ाइल में सारणी है: पंक्तियाँ रिकॉर्ड हैं, और मान कॉमा से अलग होते हैं। मॉड्यूल csv कोट, मानों के भीतर कॉमा और पंक्ति-ब्रेक ठीक से संभालता है — जो हाथ से लिखा split(",") नहीं करेगा।

import csv

with open("data/expenses.csv", newline="", encoding="utf-8") as f:
    reader = csv.DictReader(f)
    total = 0.0
    for row in reader:
        total += float(row["amount"])
        print(row["date"], row["category"], row["amount"])
print("कुल:", total)

csv.DictReader हर पंक्ति को फ़ाइल के हेडर के अनुसार डिक्शनरी बनाता है। सारे मान स्ट्रिंग होते हैं: संख्याएँ और तारीख़ें ख़ुद बदलें (float, int, date.fromisoformat)। जिस फ़ाइल में विभाजक «;» है (रूसी Excel ऐसे ही सहेजता है), उसे delimiter=";" से पढ़ें।

rows = [
    {"date": "2026-10-01", "category": "खाना", "amount": 450},
    {"date": "2026-10-02", "category": "यात्रा", "amount": 60},
]
with open("data/out.csv", "w", newline="", encoding="utf-8") as f:
    writer = csv.DictWriter(f, fieldnames=["date", "category", "amount"])
    writer.writeheader()
    writer.writerows(rows)

लिखते समय newline="" ज़रूरी है: उसके बिना Windows पर पंक्तियों के बीच खाली पंक्तियाँ आ जाएँगी। अगर फ़ाइल Excel में खोली जाएगी, तो encoding="utf-8-sig" लें — BOM चिह्न Excel को UTF-8 पहचानने में मदद करता है।

CSV से JSON: पूरा उदाहरण

import csv
import json
from collections import defaultdict
from pathlib import Path

src = Path("data/expenses.csv")
dst = Path("data/report.json")

by_category = defaultdict(float)
with src.open(newline="", encoding="utf-8") as f:
    for row in csv.DictReader(f):
        by_category[row["category"]] += float(row["amount"])

report = {"total": sum(by_category.values()), "categories": dict(by_category)}
dst.write_text(json.dumps(report, ensure_ascii=False, indent=2), encoding="utf-8")
print(dst.read_text(encoding="utf-8"))

किसी भी रिपोर्ट-स्क्रिप्ट का मूल ढाँचा यही है: CSV से इनपुट, डिक्शनरी में एकत्रीकरण, JSON में आउटपुट।

आम गलतियाँ

  • FileNotFoundError — पथ सापेक्ष है और मौजूदा फ़ोल्डर से गिना जाता है, स्क्रिप्ट के फ़ोल्डर से नहीं। Path(__file__).parent लें।
  • फ़ाइल खाली हो गई — "w" की जगह "a" लेना था।
  • UnicodeDecodeError — फ़ाइल किसी और एन्कोडिंग में है; उसे साफ़ लिखें (cp1251, utf-8-sig)।
  • TypeError: Object of type set is not JSON serializable — सूची में बदलें या default दें।
  • JSON लोड करने के बाद KeyError — संख्यात्मक कुंजियाँ स्ट्रिंग बन चुकी हैं।
  • अपनी फ़ाइल का नाम json.py या csv.py रख दिया — वह स्टैंडर्ड मॉड्यूल को ढक लेती है, और import json आपकी फ़ाइल को इम्पोर्ट करता है।

निष्कर्ष

JSON के लिए Python की स्टैंडर्ड लाइब्रेरी काफ़ी है: फ़ाइलों के लिए json.load/json.dump, स्ट्रिंग के लिए loads/dumps, और पढ़ने योग्य आउटपुट के लिए ensure_ascii=False और indent। फ़ाइलें with से साफ़ एन्कोडिंग के साथ खोलें, पथ pathlib से बनाएँ, सारणी को csv.DictReader से पढ़ें। कोर्स में यह विषय व्यवहार में सिखाया जाता है: ख़र्च ट्रैकर CSV से ख़र्च पढ़ता है और रिपोर्ट JSON में सहेजता है।

अक्सर पूछे जाने वाले प्रश्न

json.load और json.loads में क्या फ़र्क है?

json.load खुले फ़ाइल-ऑब्जेक्ट से JSON पढ़ता है, और json.loads स्ट्रिंग को पार्स करता है। इसी तरह json.dump फ़ाइल में लिखता है, और json.dumps स्ट्रिंग लौटाता है।

JSON में हिंदी अक्षर \u-कोड के बिना कैसे सहेजें?

json.dump या json.dumps में ensure_ascii=False दें और फ़ाइल को encoding="utf-8" से खोलें।

JSON के साथ काम करने के लिए कोई लाइब्रेरी इंस्टॉल करनी होगी?

नहीं, मॉड्यूल json स्टैंडर्ड लाइब्रेरी में है; बस import json लिखना काफ़ी है।

क्या JSON में तारीख़ या सेट रखा जा सकता है?

सीधे नहीं। उन्हें बदलना होगा, जैसे तारीख़ को isoformat से ISO स्ट्रिंग में और सेट को सूची में, या default पैरामीटर में फ़ंक्शन देना होगा।

बहुत बड़ा JSON, जो मेमोरी में नहीं आता, कैसे पढ़ें?

मानक json.load पूरी फ़ाइल पढ़ता है; बड़े डेटा के लिए JSON Lines फ़ॉर्मैट रखें और json.loads से पंक्ति-दर-पंक्ति पार्स करें।

इस विषय को वीडियो में सीखें

यह विषय “Python 3.15: от новичка до профи” कोर्स में अभ्यास के साथ विस्तार से समझाया गया है।

कोर्स पर जाएँ