2009-09-03 13 views
10

एक फ़ाइल की सामग्री को पढ़ने के लिए:फ़ाइल खोलें: क्या यह खराब पायथन शैली है?

data = open(filename, "r").read() 

फ़ाइल खोलने तुरंत कहीं भी संदर्भित किया जा रहा बंद हो जाता है, तो फ़ाइल वस्तु अंततः करीब ... और यह अन्य कार्यक्रमों का उपयोग कर प्रभावित नहीं होना चाहिए होगा, के बाद से फाइल है केवल पढ़ने के लिए खुला, लिखना नहीं।

संपादित करें: यह वास्तव में मुझे एक परियोजना में लिखा है - मैंने मुझे this प्रश्न पूछने के लिए प्रेरित किया। फ़ाइल ऑब्जेक्ट केवल तभी साफ हो जाते हैं जब आप स्मृति से बाहर हो जाते हैं, न कि जब आप फ़ाइल हैंडल से बाहर होते हैं। तो यदि आप इसे अक्सर करते हैं, तो आप फ़ाइल डिस्क्रिप्टर से बाहर निकल सकते हैं और अपवादों को फेंकने के लिए फ़ाइलों को खोलने पर आपके आईओ प्रयासों को समाप्त कर सकते हैं।

+3

ध्यान दें कि यह पूरी फ़ाइल को स्मृति में पढ़ेगा, भले ही यह कितना बड़ा हो। तो सुनिश्चित करें कि यह एक फ़ाइल है जिसे आप संभाल सकते हैं। इसके अलावा, मैं जवाब से सहमत हूं। – balpha

+0

@balpha: लेकिन उत्तर विरोधाभासी हैं। ;) (मुझे लगता है कि आपने सभी उत्तरों में शामिल होने से पहले टिप्पणी की थी।) –

उत्तर

29
बस रिकार्ड के लिए

: यह केवल थोड़ा लंबा है, और तुरंत फ़ाइल बंद कर देता है:

from __future__ import with_statement 

with open(filename, "r") as f: 
    data = f.read() 
+4

+1 मैंने पाइथन 2.5 का उपयोग कर रहे हैं तो 'आयात' जोड़ा है :) –

+0

एक अनुवर्ती शैली प्रश्न: क्या यह खुले ("t1.py", "r") के साथ * f: f के साथ वास्तव में भयानक है। एक पंक्ति पर पढ़ें() * सब? मुझे पता है कि यह पठनीय नहीं है, लेकिन अक्सर, फ़ाइल में पढ़ने का एक बहुत ही बुनियादी प्रकार है, और कोड पढ़ने वाले अगले व्यक्ति को वास्तव में परवाह नहीं है कि आपने यह कैसे किया। –

+0

@ जेन डी: 'साथ' का एक बिंदु सभी प्रसंस्करण को एक साफ दायरे में सीमित करना है। 'खोलने के साथ') को f: f.read() 'के रूप में एक पंक्ति प्रकार में' साथ 'के स्कोपिंग उद्देश्य को हरा देता है। –

3

नहीं, यह आपके तर्क के अनुसार, पूरी तरह से उचित पायथन शैली आईएमओ है।

अद्यतन: यहां पर बहुत सारी टिप्पणियां हैं कि फाइल ऑब्जेक्ट्स सीधे दूर हो या नहीं। अटकलों की बजाय, मैंने कुछ खुदाई की।


पायथन के object.h में एक टिप्पणी से:: यहाँ मैं क्या देखते हैं

मैक्रो Py_INCREF (सेशन) और Py_DECREF (सेशन) बढ़ाने के लिए उपयोग किया जाता है या घटती संदर्भ में गिना जाता है।

समारोह तालिका फ़ाइल के लिए वस्तुओं file_dealloc कार्य करने के लिए अंक जब refcount को 0

पायथन के fileobject.c में देख रहे हैं गिर जाता है Py_DECREF वस्तु की deallocator कॉल कार्य करते हैं। यह फ़ंक्शन close_the_file पर कॉल करता है, जो बदले में फ़ाइल को बंद करता है।


तो यह कहना उचित लगता है कि फिलहाल, सीपीथॉन पर, जब फ़ाइल ऑब्जेक्ट के अधिक संदर्भ नहीं हैं, तो यह बिना किसी देरी के बंद हो जाता है। अगर आपको लगता है कि यह व्याख्या गलत है, तो कृपया एक टिप्पणी पोस्ट करें जो दर्शाती है कि आप ऐसा क्यों महसूस करते हैं।

+0

उचित, अभी तक, लेकिन ओएस संसाधन पूरी तरह से उपलब्ध नहीं हो सकते हैं। उदाहरण के लिए, इसे पढ़ने के तुरंत बाद फ़ाइल को निकालने का प्रयास करना काम नहीं कर सकता क्योंकि ओएस संसाधन अंतर्निहित सी पुस्तकालयों द्वारा आयोजित किए जाते हैं, यहां तक ​​कि सोचा था कि पायथन 'फ़ाइल' ऑब्जेक्ट कचरा एकत्रित किया गया है। जब तक ओएस सोचता है कि फ़ाइल अब उपयोग में नहीं है, तो आप इसे हटाने में सक्षम नहीं हो सकते हैं। –

+0

@ एस लॉट: क्या आप कह रहे हैं कि एक कचरा एकत्रित 'फ़ाइल' ऑब्जेक्ट बंद नहीं है (ताकि ओएस जानता है कि यह अब उपयोग में नहीं है)? मैं * उम्मीद करता हूं कि फ़ाइल ऑब्जेक्ट को हटाने से फ़ाइल बंद हो जाती है, लेकिन मुझे दस्तावेज़ में कुछ भी नहीं मिल रहा है। – EOL

+5

मेरी समझ यह है कि सीपीथॉन (संदर्भ कार्यान्वयन जो ज्यादातर लोग सोचते हैं कि जब वे पाइथन सोचते हैं) वास्तव में सभी अपरिवर्तित वस्तुओं को नष्ट कर देते हैं क्योंकि वे गुंजाइश छोड़ देते हैं। उस स्थिति में, फ़ाइल ऑब्जेक्ट जैसे ही पढ़ा जाता है() ऑपरेशन पूरा हो जाता है। तो यह वही करना चाहिए जो आप चाहते हैं। हालांकि, यह गारंटीकृत व्यवहार नहीं है। पायथन के अन्य कार्यान्वयन (ज्योथन मुझे लगता है कि एक प्रमुख उदाहरण है) कचरा संग्रह को अलग-अलग संभाल सकता है। यदि आप जानते हैं कि आप सीपीथॉन का उपयोग कर रहे हैं और पोर्टेबिलिटी की परवाह नहीं करते हैं तो मेरा वृत्ति सरल कार्यान्वयन का उपयोग करना है। –

1

मुझे ठीक लग रहा है .. मैंने अक्सर इस तरह की फाइलें पढ़ीं।

6

यह सच है कि यह अंततः बंद हो जाएगा, लेकिन अंततः जल्द ही पर्याप्त नहीं हो सकता है। विशेष रूप से यदि आप इसे लूप के अंदर उपयोग कर रहे हैं, तो जीसी फाइल ऑब्जेक्ट्स पर पहुंचने से पहले सिस्टम फ़ाइल हैंडल से बाहर हो सकता है।

+0

ओह, कभी सोचा नहीं! – Claudiu

+0

लेकिन अगर fileobj संदर्भ गिना जाता है .. यह सीधे 0 पर जाता है और तुरंत हटा दिया जाता है? सीपीथॉन (?) में। – u0b34a0f6ae

+0

@ kaizer.se: यह अभी भी जरूरी नहीं है कि तुरंत हटा दिया जाए। केवल जब सीपीथन को और अधिक स्मृति की आवश्यकता होती है। – Claudiu

4

कोड वास्तव में काम करता है के रूप में आप कहते हैं कि यह करता है, लेकिन यह बुरा शैली फिर भी है। आपका कोड उन धारणाओं पर निर्भर करता है जो अब सच हो सकते हैं, लेकिन हमेशा सत्य नहीं होंगे। यह असंभव नहीं है कि आपका कोड उस स्थिति में चलाया जाएगा जहां फ़ाइल खोला जा रहा है और बंद नहीं है मामला। क्या कोड के 1 या 2 लाइनों को सहेजने के लिए यह वास्तव में जोखिम है? मुझे ऐसा नहीं लगता।

2

भले ही यह काम करता है के रूप में उम्मीद, मैं इसे दो मायने रखता है में विफल रहता है लगता है:

  1. आपका कोड, मूल पैमाने नहीं होगा क्योंकि आप स्मृति में पूरी फ़ाइल पढ़ रहे हैं, और इस या नहीं हो सकता जरूरी है कि आप क्या चाहते हैं।
  2. पायथन के जेन के अनुसार (पाइथन प्रॉम्प्ट में import this को पुनः प्राप्त करने के लिए प्रयास करें) "स्पष्ट रूप से स्पष्ट स्पष्ट है" और, फ़ाइल को स्पष्ट रूप से बंद करने में विफल होने के कारण, आप किसी को भ्रमित कर सकते हैं, सड़क के नीचे, छोड़ा जाएगा रखरखाव के लिए अपने कोड के साथ।

यह वास्तव में स्पष्ट होने में मदद करता है! पायथन स्पष्ट शैली को प्रोत्साहित करता है।

इसके अलावा, एक फेंकने वाली लिपि के लिए, आपकी शैली समझ में आता है।

शायद आपको this answer से लाभ होगा।

संबंधित मुद्दे