2011-12-22 27 views
6

मैं एक बैच फ़ाइल बनाने की कोशिश कर रहा हूं जो विंडोज़ के संस्करण के आधार पर अलग-अलग 'पसंद' कमांड करता है। विंडोज 7 और विंडोज एक्सपी के बीच पसंद कमांड का सिंटैक्स अलग है।बैच फ़ाइल 'पसंद' कमांड का एररलेवल रिटर्न 0

विकल्प आदेश देता है वाई के लिए एक 1 और 2 एन के लिए निम्न आदेश देता है सही त्रुटि का स्तर:

विंडोज 7:

choice /t 5 /d Y /m "Do you want to automatically shutdown the computer afterwards " 
echo %errorlevel% 
if '%errorlevel%'=='1' set Shutdown=T 
if '%errorlevel%'=='2' set Shutdown=F 

Windows XP:

choice /t:Y,5 "Do you want to automatically shutdown the computer afterwards " 
echo %ERRORLEVEL% 
if '%ERRORLEVEL%'=='1' set Shutdown=T 
if '%ERRORLEVEL%'=='2' set Shutdown=F 

हालांकि , जब इसे विंडोज ओएस संस्करण का पता लगाने के लिए एक कमांड के साथ जोड़ा जाता है, तो त्रुटि के बाद मेरे विंडोज एक्सपी और विंडोज 7 ब्लॉक कोड में विकल्प कमांड के बाद एएनएल से पहले 0 लौटाता है।

REM Windows XP 
ver | findstr /i "5\.1\." > nul 
if '%errorlevel%'=='0' (
set errorlevel='' 
echo %errorlevel% 
choice /t:Y,5 "Do you want to automatically shutdown the computer afterwards " 
echo %ERRORLEVEL% 
if '%ERRORLEVEL%'=='1' set Shutdown=T 
if '%ERRORLEVEL%'=='2' set Shutdown=F 
echo. 
) 

REM Windows 7 
ver | findstr /i "6\.1\." > nul 
if '%errorlevel%'=='0' (
set errorlevel='' 
echo %errorlevel% 
choice /t 5 /d Y /m "Do you want to automatically shutdown the computer afterwards " 
echo %errorlevel% 
if '%errorlevel%'=='1' set Shutdown=T 
if '%errorlevel%'=='2' set Shutdown=F 
echo. 
) 

आप देख सकते हैं, मैं भी पसंद आदेश निष्पादित करने से पहले errorlevel वर समाशोधन कोशिश की, लेकिन errorlevel के बाद चुनाव कमांड निष्पादित किया जाता है 0 पर बनी हुई है।

कोई सुझाव? धन्यवाद!

उत्तर

13

आपने क्लासिक समस्या से भाग लिया है - आप कोड के एक संश्लेषित ब्लॉक के भीतर %errorlevel% का विस्तार करने का प्रयास कर रहे हैं। विस्तार का वह रूप पार्स समय पर होता है, लेकिन पूरे आईएफ निर्माण को एक बार में पार्स किया जाता है, इसलिए %errorlevel% का मान नहीं बदलेगा।

समाधान सरल है - देरी विस्तार। आपको शीर्ष पर SETLOCAL EnableDelayedExpansion की आवश्यकता है, और उसके बाद !errorlevel! का उपयोग करें। विलंबित विस्तार निष्पादन समय पर होता है, इसलिए आप कोष्ठक के भीतर मान में परिवर्तन देखने में सक्षम होते हैं।

एसईटी (SET /?) के लिए सहायता एक फोर स्टेटमेंट के संबंध में समस्या और समाधान का वर्णन करती है, लेकिन अवधारणा वही है।

आपके पास अन्य विकल्प हैं।

आप कोष्ठकों के बिना कोड के लेबल वर्गों के लिए IF के शरीर के भीतर से कोड ले जाते हैं, और कोड का उपयोग करने की GOTO या CALL उपयोग कर सकते हैं। फिर आप %errorlevel% का उपयोग कर सकते हैं। मुझे यह विकल्प पसंद नहीं है क्योंकि CALL और GOTO अपेक्षाकृत धीमी हैं, और कोड कम सुरुचिपूर्ण है।

एक और विकल्प IF !ERRORLEVEL!==N के बजाय IF ERRORLEVEL N का उपयोग करना है। (IF /? देखें) क्योंकि IF ERRORLEVEL N त्रुटि अगर त्रुटि है> = एन, आपको अवरोही क्रम में अपने परीक्षण करने की आवश्यकता है।

REM Windows XP 
ver | findstr /i "5\.1\." > nul 
if '%errorlevel%'=='0' (
    choice /t:Y,5 "Do you want to automatically shutdown the computer afterwards " 
    if ERRORLEVEL 2 set Shutdown=F 
    if ERRORLEVEL 1 set Shutdown=T 
)