2015-05-24 9 views
6

जब खुली फ़ाइलों के साथ काम कर का उपयोग करते समय, अजगर with वाक्य रचना सुनिश्चित करें कि फ़ाइल बंद कर देता है जब ब्लॉक छोड़ने बनाता है - अपवाद आदि की परवाह किए बिनाअपवाद संचालन पायथन के subprocess.Popen

with open('foo.txt') as f: 
    foo = f.read() 

के बाद से प्रक्रियाओं संसाधन भी हैं , मैं सोच रहा था: Popen का उपयोग करते समय कुछ ऐसा संभव या अनुशंसित है? उदाहरण के लिए, Popen.kill(); Popen.communicate()finally खंड में चलाना चाहिए - मान लीजिए कि प्रक्रिया समाप्त होने तक मुझे अवरुद्ध नहीं करना चाहिए?

+1

आप एक संस्करण पूर्व अजगर 3.2 चल रहे थे तो। आप '__enter__' और' __exit__' जादू विधियों के साथ 'कक्षा' का उपयोग करने के लिए बस एक कक्षा को परिभाषित कर सकते हैं। –

उत्तर

6

पायथन 3.2 Popen से शुरू एक संदर्भ प्रबंधक है।

docs से

:

popen वस्तुओं बयान के साथ के माध्यम से संदर्भ प्रबंधक के रूप में समर्थित हैं: बाहर निकलने पर, मानक फ़ाइल वर्णनकर्ता बंद हो जाती हैं, और इस प्रक्रिया के लिए इंतजार कर रहे थे है।

यह आपको जो कुछ चाहिए वो करना चाहिए।

def __enter__(self): 
    return self 

def __exit__(self, type, value, traceback): 
    if self.stdout: 
     self.stdout.close() 
    if self.stderr: 
     self.stderr.close() 
    if self.stdin: 
     self.stdin.close() 
    # Wait for the process to terminate, to avoid zombies. 
    self.wait() 

अब तुम अजगर 2,7

from subprocess import Popen 

class MyPopen(Popen): 

    def __enter__(self): 
     return self 

    def __exit__(self, type, value, traceback): 
     if self.stdout: 
      self.stdout.close() 
     if self.stderr: 
      self.stderr.close() 
     if self.stdin: 
      self.stdin.close() 
     # Wait for the process to terminate, to avoid zombies. 
     self.wait() 

if __name__ == '__main__': 
    with MyPopen(['ls']) as p: 
     print(p) 
+0

ठीक है, शांत। तो ऐसा लगता है कि इसे पायथन 2.7 में भी करने का बुरा विचार नहीं है, 'कोशिश करें ... अंत में' – z0r

+0

मैंने पायथन 3.4 से कोड कॉपी करके एक पायथन 2.7 संस्करण जोड़ा। हालांकि कुछ परीक्षण की आवश्यकता हो सकती है। ;) –

+1

@ z0r: 'subprocess32' मॉड्यूल है जिसे आप पाइथन 2.7 पर इंस्टॉल कर सकते हैं (यह अन्य सुधार भी प्रदान करता है। हालांकि यह गैर-पॉज़िक्स सिस्टम पर काम नहीं कर सकता है)। – jfs

2

में कर सकते हैं आप किसी भी करने के लिए सिर्फ दो कस्टम तरीकों जोड़ सकते हैं:

यह मानक lib से subprocess.py से प्रासंगिक हिस्सा अजगर 3.4 में है with कथन के साथ comptability लागू करने के लिए कक्षा।

class CustomObject(object): 
    def __enter__(self): 
     """ This method execudes when entering block. """ 
     return thing_you_want_to_use 

    def __exit__(self, type, value, traceback): 
     """ This method execudes on block exit. """ 
     # Tear things down. 
3

2,7 के लिए आप भी इस्तेमाल कर सकते हैं @contextlib.contextmanager:

import contextlib 

@contextlib.contextmanager 
def manage_process(process): 
    try: 
     yield process 
    finally: 
     for stream in [process.stdout, process.stdin, process.stderr]: 
      if stream: 
       stream.close() 
     process.wait() 

उदाहरण के लिए:

with manage_process(Popen(['ls'])) as p: 
    print(p) 
संबंधित मुद्दे