2013-04-14 3 views
7

कृपया ध्यान दें: यह eval() के उपयोग के बारे में नहीं है, यह उस पुस्तक की संभावित गुणवत्ता (या इसकी कमी) के बारे में है जिसका उपयोग किया जाता है और सिखाया जाता है। इसलिए पहले से ही पाइथन में eval() के बारे में अनगिनत धागे हैं।पायथन - ज़ेल पुस्तक eval() का उपयोग करता है, क्या यह गलत है?

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

यह प्रश्न कुख्यात eval() फ़ंक्शन के उपयोग के बारे में है।

एक अपेक्षाकृत अच्छी तरह से ज्ञात (और अच्छी तरह से समीक्षा की है, जैसा कि आप देख सकते हैं) जॉन Zelle द्वारा किताब है: http://www.amazon.com/Python-Programming-Introduction-Computer-Science/dp/1590282418/ref=pd_sim_b_3

तकनीकी तौर पर, यह एक CS1 पुस्तक जो प्रोग्रामिंग भाषा के रूप में अजगर का उपयोग करता है। काफी उचित है, इस तरह के लेखक के कंधों से कुछ जिम्मेदारी लेती है ("अरे, मैं आपको यहां कुछ व्यापक सिखाता हूं, इन सभी वाक्यविन्यास और सुरक्षा विवरण नहीं"), लेकिन जब मैंने इसे पढ़ना शुरू किया, मैंने देखा, सचमुच बहुत पहला उदाहरण है, जहां एक्स एक पूर्णांक होना चाहिए और इस तरह हम एक पूर्णांक में उपयोगकर्ता इनपुट बदलने की आवश्यकता

x = eval(input("Enter your number: "))

का उपयोग।

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

तो, मैं मानता हूं, मैं पुस्तक में बहुत दूर नहीं हूं, लेकिन मैं इस बिंदु पर पहुंच गया हूं, थोड़ी देर बाद, लेखक ने अपने विवादास्पद प्रकृति के संदर्भ के बिना eval() के उपयोग की व्याख्या की। उन्होंने मूल रूप से कहा कि मैंने अभी क्या कहा है: हमें अंततः एक int होने के लिए x की आवश्यकता है, इसलिए ऐसा करने का एक आसान तरीका यहां है। और ऐसा लगता है कि वह कभी भी इसका इस्तेमाल कर रहा है।

मेरा प्रश्न यह है: यदि, शुरुआत से ही, कोई लेखक ऐसी गलती करता है (या यह कोई गलती नहीं है? मुझे यहां कुछ याद आ रही है), क्या यह सीखने योग्य पुस्तक है? मेरा मानना ​​है कि श्री ज़ेल सीएस का एक महान शिक्षक है, और यह दिखाता है, लेकिन चाहे वह चाहे या नहीं, लोग अब भी अपनी पुस्तक से पाइथन सीखेंगे, साथ ही एल्गोरिदम और प्रोग्रामिंग की कला के अलावा। तो क्या पाइथन को ऐसी किताब से सीखना उचित है जो पाइथन समुदाय में इस तरह के एक सार्वभौमिक मुद्दे पर चुप रहता है? मैं नहीं चाहता कि श्री ज़ेल एक पाइथन हैकर बनें और अपने सभी रहस्यों को उजागर करें, लेकिन इस तरह के छोटे विवरण किसी ऐसे व्यक्ति को बना या तोड़ सकते हैं जो आत्म-शिक्षण/आत्म-शिक्षण है। इस सीखने की सामग्री के संबंध में आपकी सलाह क्या होगी?

पीएस दूसरी तरफ, मुझे शुरुआत से थोड़ा सा शोध और प्रयोग (अनजाने में) करना बहुत अच्छा है :-)

धन्यवाद!

+0

मैंने सोचा था कि eval सिर्फ जावास्क्रिप्ट में बुरा था –

+5

@JasonSperske यह हर जगह बुराई है – jamylak

+4

int() के बजाय eval() को सुझाव देना गलत है। –

उत्तर

9

प्रश्न में पुस्तक के लेखक के रूप में, मुझे इस मुद्दे पर वजन कम करने दें।

पुस्तक में eval का उपयोग मुख्य रूप से पाइथन 2 से पायथन 3 में रूपांतरण का ऐतिहासिक आर्टिफैक्ट है (हालांकि पाइथन 2 में इनपुट के उपयोग में एक ही "दोष" मौजूद है)। मैं उत्पादन कोड में eval का उपयोग करने के खतरों से अच्छी तरह से अवगत हूं जहां इनपुट अविश्वसनीय स्रोत से आ सकता है, लेकिन पुस्तक वेब-आधारित सिस्टम के लिए उत्पादन कोड के बारे में नहीं है; यह कुछ सीएस और प्रोग्रामिंग सिद्धांतों को सीखने के बारे में है। पुस्तक में वास्तव में कुछ भी नहीं है जिसे दूरस्थ रूप से उत्पादन कोड माना जा सकता है। मेरा लक्ष्य हमेशा सबसे सरल दृष्टिकोण का उपयोग करना है जो मुझे उस बिंदु को स्पष्ट करने की अनुमति देता है जिसे मैं बनाने की कोशिश कर रहा हूं, और eval ऐसा करने में मदद करता है।

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

निचली पंक्ति यह है कि इस पुस्तक को बेहतर बनाने के कई तरीके हैं (वहां हमेशा हैं)। मुझे नहीं लगता कि eval का उपयोग करना एक घातक दोष है; यह उन कार्यक्रमों के प्रकारों के लिए उपयुक्त है जो संदर्भित किए जा रहे हैं और संदर्भ जिसमें वे प्रोग्राम दिखाई देते हैं।मुझे पुस्तक में पाइथन का उपयोग करने के तरीके में किसी भी अन्य "असुरक्षा" से अवगत नहीं है, लेकिन आपको चेतावनी दी जानी चाहिए (जैसा कि प्रस्तावना बताता है) कि वहां कई जगहें हैं जहां कोड बिल्कुल "पायथनिक" नहीं है।

+5

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

+0

मुझे लगता है कि सर्वोत्तम पुस्तकें वे हैं जिनमें लेखक पहुंच योग्य है। तो, शायद, इस संबंध में आपका तीसरा जोड़ा बेहतर होगा। ऐसा कहा जा रहा है कि, मैं आपसे असहमत हूं कि eval() का उपयोग एक "पायथनिक" मुद्दा है। मेरा मानना ​​है कि यह एक मौलिक मुद्दा है कि पुस्तक के पाठक सही तरीके से काम करना सीखेंगे या नहीं। मैं आपसे सहमत हूं कि आपको पाइथन 3 कोड लिखने के इतिहास से पीड़ित नहीं होने वाली सुरक्षा स्तरीय सुरक्षा का जिक्र करना चाहिए, जो आपकी स्क्रिप्ट्स, या इससे भी बेहतर है। – Kaydell

2

हाँ eval को इसके बारे में लोगों को चेतावनी देने के बजाय evil वर्तनी की जानी चाहिए;) आपको इसे तब तक प्रयास करना चाहिए जब तक कि आपको बिल्कुल यह नहीं करना चाहिए। इस मामले में इसके बजाय int() का उपयोग करने के लिए सहज है, यह और भी अधिक पठनीय है!अगर आपको वास्तव में ast.literal_eval का उपयोग करना पड़ता है (यह केवल शाब्दिक मूल्यांकन करता है क्योंकि नाम का तात्पर्य है, इसलिए यह उपयोगकर्ता को दुर्भावनापूर्ण कोड चलाने की अनुमति नहीं देगा) जो वास्तव में सुरक्षित है, लेकिन इसके लिए कोई आवश्यकता नहीं है और इसकी आवश्यकता नहीं है इस मामले में eval() के लिए।

+0

को दोषी ठहराती है धन्यवाद! मेरा सवाल, हालांकि, इस तरह के कोड पर एक सम्मानित प्रोफेसर से सीएस-पायथन पुस्तक में उपस्थित होने पर आपकी राय के बारे में कुछ और था, जिसे शुरुआती सैद्धांतिक रूप से पूरी तरह से भरोसा करना चाहिए। क्या यह एक बुरी किताब है या सिर्फ एक छोटी गलती है जिसे उसने सामग्री की गुणवत्ता के बारे में और कुछ नहीं कहना चाहिए? – Leo

4

चूंकि eval जगह से बाहर है और आपके द्वारा दिए गए उदाहरण में अनावश्यक है, तो मुझे निश्चित रूप से पुस्तक के अन्य हिस्सों की सुरक्षा के बारे में संदेह होगा। क्या लेखक यह सुझाव देने जा रहा है कि आप किसी उपयोगकर्ता क्वेरी को एसक्यूएल क्वेरी में जोड़ते हैं?

मुझे लगता है कि लेखक के ईमेल पते को ढूंढने और उसे सीधे इसके बारे में पूछने के लायक हो सकता है।

+0

धन्यवाद! मैंने ऐसा करने पर विचार किया लेकिन फिर पृथ्वी पर कौन सी सीएस प्रोफेसर से सवाल कर रहा हूं? मैं सिर्फ एक शौकिया अर्द्ध प्रोग्रामर हूं जिसमें मेरी बेल्ट के तहत बहुत कम परियोजनाएं हैं। मेरी विश्वविद्यालय की डिग्री में कंप्यूटर या किसी भी तकनीक के साथ कुछ लेना देना नहीं है। यह बहुत अधिक संभावना है कि मैं यहां मूर्ख हूं और नहीं। यह सिर्फ अजीब है ... विश्वविद्यालयों में उपयोग की जाने वाली एक पुस्तक, निश्चित रूप से किसी ने अब तक इस प्रश्न से पूछा होगा, लेकिन Google कुछ भी नहीं देता है। – Leo

+0

@Gleb - लेकिन आप पूरी तरह से अपने ज्ञान के आधार पर 'eval' के उपयोग पर सवाल नहीं उठा रहे हैं। [आप इस पर अकेले नहीं हैं] (http://nedbatchelder.com/blog/201206/eval_really_is_dangerous.html), तो बस जाओ और पूछें। आपके पास खोने के लिए क्या है? – root

+1

मुझे लेखक का ईमेल मिला और उसे इसके बारे में पूछा। हर कोई कहता है कि वह एक महान लड़का है, उम्मीद है कि वह मुझ पर पागल नहीं होगा :-) अगर शुरुआती लोगों को सुरक्षा की परवाह नहीं करनी चाहिए, तो भी इस वेबसाइट की तरह कहीं भी कोड का एक स्निपेट सबमिट करना और बाधा का सामना करना हमेशा निराशाजनक होता है। .. ठीक है, नफरत नहीं, ज़ाहिर है, लेकिन इस तरह की आलोचना का बंधन "किसने आपको यह तरीका करने के लिए सिखाया 0_o?" – Leo

3

ठीक है, इस तरह से eval() और इनपुट() को गठबंधन करने के लिए एक प्राथमिक लेकिन संभवतः बहुत हानिकारक 'खोल' बनाता है। मैंने पुस्तक नहीं पढ़ी है, लेकिन मैं इसे नमक के अनाज के साथ ले जाऊंगा। यह सिर्फ बुरा अभ्यास नहीं है, यह कार्यों के एक घातक कॉम्बो लागू करता है।

5

हाँ, यह गलत है। लेकिन मुझे लगता है कि मुझे पता है कि यह वहां क्यों है।

बहुत सारे लोग पाइथन 2.x में input() का उपयोग करते हैं, जो बहुत दुर्भाग्य से नामित फ़ंक्शन है क्योंकि यह केवल इनपुट नहीं पढ़ता है, यह इसका मूल्यांकन भी करता है। कनवर्टर 2to3, eval(input()) करने के लिए input() में से प्रत्येक के उपयोग धर्मान्तरित के रूप में आप देख सकते हैं:

$ cat test.py 
x = input("Enter your number: ") 

$ 2to3 test.py 
RefactoringTool: Skipping implicit fixer: buffer 
RefactoringTool: Skipping implicit fixer: idioms 
RefactoringTool: Skipping implicit fixer: set_literal 
RefactoringTool: Skipping implicit fixer: ws_comma 
RefactoringTool: Refactored test.py 
--- test.py  (original) 
+++ test.py  (refactored) 
@@ -1 +1 @@ 
-x = input("Enter your number: ") 
+x = eval(input("Enter your number: ")) 
RefactoringTool: Files that need to be modified: 
RefactoringTool: test.py 

तो मेरा अनुमान है कि यह सिर्फ एक छोटे से खराब है। अमेज़न वर्णन से:

यह अच्छी तरह से पर्याप्त उत्पादन की जाँच के बिना जॉन Zelle के अजगर प्रोग्रामिंग के दूसरे संस्करण, पायथन 3.

मुझे लगता है कि किसी कोड नमूने के सभी पर 2to3 भाग गया के लिए अद्यतन है । तो हाँ, पाइथन 2.x में input() का उपयोग करने की गलती थी, और आउटपुट की जांच किए बिना 2to3 का उपयोग करना गलती थी।

+2

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

+2

तो लेखक की गलती पहली संस्करण के साथ थी जब उन्होंने raw_input() –

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