轉(zhuǎn)自:http://blog.csdn.net/wuxiushu/article/details/52358172
sys.stdout?與print??
當(dāng)我們?cè)?Python?中打印對(duì)象調(diào)用print?obj?時(shí)候让蕾,事實(shí)上是調(diào)用了?sys.stdout.write(obj+'\n')??
print?將你需要的內(nèi)容打印到了控制臺(tái)倦西,然后追加了一個(gè)換行符逛揩。print?會(huì)調(diào)用?sys.stdout?的?write?方法??
以下兩行在事實(shí)上等價(jià):??
sys.stdout.write('hello'+'\n')???
print?'hello'??
sys.stdin?與?raw_input??
當(dāng)我們用?raw_input('Input?promption:?')?時(shí),事實(shí)上是先把提示信息輸出商膊,然后捕獲輸入??
以下兩組在事實(shí)上等價(jià):??
hi=raw_input('hello??')? ?
print?'hello??',?#comma?to?stay?in?the?same?line???
hi=sys.stdin.readline()[:-1]?#?-1?to?discard?the?'\n'?in?input?stream??
從控制臺(tái)重定向到文件??
原始的?sys.stdout?指向控制臺(tái)??
如果把文件的對(duì)象的引用賦給?sys.stdout,那么print?調(diào)用的就是文件對(duì)象的?write?方法??
f_handler=open('out.log',?'w')???
sys.stdout=f_handler???
print?'hello'??
#?this?hello?can't?be?viewed?on?concole???
#?this?hello?is?in?file?out.log??
記住矛双,如果你還想在控制臺(tái)打印一些東西的話汪拥,最好先將原始的控制臺(tái)對(duì)象引用保存下來(lái),向文件中打印之后再恢復(fù)?sys.stdout??
__console__=sys.stdout???
#?redirection?start?#???
...???
#?redirection?end???
sys.stdout=__console__??
同時(shí)重定向到控制臺(tái)和文件??
如果我們希望打印的內(nèi)容一方面輸出到控制臺(tái)陋气,另一方面輸出到文件作為日志保存劳吠,那么該怎么辦???
將打印的內(nèi)容保留在內(nèi)存中巩趁,而不是一打印就將?buffer?釋放刷新赴背,那么放到一個(gè)字符串區(qū)域中會(huì)怎樣???
a=''???
sys.stdout=a???
print?'hello'??
OK,上述代碼是無(wú)法正常運(yùn)行的??
Traceback?(most?recent?call?last):?File???
".\hello.py",?line?xx,?in?print?'hello'???
AttributeError:'str'???
object?has?no?attribute'write'??
錯(cuò)誤很明顯凰荚,就是上面強(qiáng)調(diào)過(guò)的燃观,在嘗試調(diào)用?sys.stdout.write()?的時(shí)候,發(fā)現(xiàn)沒(méi)有?write?方法??
另外便瑟,這里之所以提示?attribute?error?而不是找不到函數(shù)等等缆毁,我猜想是因?yàn)?python?將對(duì)象/類(lèi)的函數(shù)指針記錄作為對(duì)象/類(lèi)的一個(gè)屬性來(lái)對(duì)待,只是保留了函數(shù)的入口地址??
既然這樣到涂,那么我們必須給重定向到的對(duì)象實(shí)現(xiàn)一個(gè)?write?方法:??
import?sys???
class?__redirection__:???
def?__init__(self):???
self.buff=''???
self.__console__=sys.stdout???
def?write(self,?output_stream):???
self.buff+=output_stream???
def?to_console(self):???
sys.stdout=self.__console__???
print?self.buff???
def?to_file(self,?file_path):??
f=open(file_path,'w')???
????sys.stdout=f???
print?self.buff???
????f.close()???
def?flush(self):???
self.buff=''???
def?reset(self):???
sys.stdout=self.__console__???
if?__name__=="__main__":???
#?redirection???
??r_obj=__redirection__()???
??sys.stdout=r_obj??
#?get?output?stream???
print?'hello'???
print?'there'???
#?redirect?to?console???
??r_obj.to_console()???
#?redirect?to?file???
r_obj.to_file('out.log')???
#?flush?buffer??
??r_obj.flush()???
#?reset???
??r_obj.reset()??
同樣的脊框,sys.stderr,?sys.stdin?也都可以被重定向到多個(gè)地址,舉一反三的事情就自己動(dòng)手實(shí)踐吧 ?