सवाल यह निर्धारित करने के लिए कि कोई बैश चर खाली है या नहीं?


यह निर्धारित करने का सबसे अच्छा तरीका क्या है कि बैश में एक चर खाली है ("")?

मैंने सुना है कि यह सिफारिश की जाती है कि मैं करता हूं if [ "x$variable" = "x" ]

है कि सही बात मार्ग? (कुछ और सरल होना चाहिए)


719
2018-05-12 17:54


मूल




जवाब:


यदि कोई चर सेट न हो या खाली स्ट्रिंग ("") पर सेट हो तो यह सच हो जाएगा।

if [ -z "$VAR" ];

980
2018-05-12 18:06



क्या इसमें कोई वैरिएबल आईएस सेट है जो "" के मान पर है? - Brent
हां यह करता है ... शून्य-लंबाई स्ट्रिंग के लिए "-z" परीक्षण। - David Z
if [ ! -z "$VAR" ]; - Aaron Copley
के विपरीत -z है -n  if [ -n "$VAR" ]; - Felipe Alvarez
डबल उद्धरण सुनिश्चित करते हैं कि चर विभाजित नहीं होता है। एक सरल $var कमांड लाइन पर इसके व्हाइटस्पेस द्वारा पैरामीटर की सूची में विभाजित किया जाएगा, जबकि "$var" हमेशा केवल एक पैरामीटर होगा। क्वोटिंग चर अक्सर एक अच्छा अभ्यास है और आपको व्हाइटस्पेस (अन्य चीजों के साथ) वाले फ़ाइल नामों पर ट्राइप करने से रोकता है। उदाहरण: करने के बाद a="x --help", प्रयत्न cat $a - यह आपको सहायता पृष्ठ देगा cat। फिर कोशिश करो cat "$a" - यह (आमतौर पर) कहेंगे cat: x --help: No such file or directory। संक्षेप में, जल्दी उद्धरण और उद्धरण अक्सर और आप लगभग कभी पछतावा नहीं करेंगे। - Score_Under


बैश में, जब आप उन गोले के पोर्टेबिलिटी से चिंतित नहीं हैं जो इसका समर्थन नहीं करते हैं, तो आपको हमेशा डबल-ब्रैकेट सिंटैक्स का उपयोग करना चाहिए:

निम्न में से कोई भी:

if [[ -z $variable ]]
if [[ -z "$variable" ]]
if [[ ! $variable ]]
if [[ ! "$variable" ]]

बैश में, डबल स्क्वायर ब्रैकेट का उपयोग करके, उद्धरण आवश्यक नहीं हैं। आप एक चर के लिए परीक्षण को सरल बना सकते हैं कर देता है इसमें एक मान है:

if [[ $variable ]]

यह वाक्यविन्यास ksh (कम से कम ksh93, वैसे भी) के साथ संगत है। यह शुद्ध पॉज़िक्स या पुराने बोर्न शैल जैसे श या डैश में काम नहीं करता है।

देख मेरा जवाब यहाँ तथा BashFAQ / 031 डबल और सिंगल स्क्वायर ब्रैकेट के बीच अंतर के बारे में अधिक जानकारी के लिए।

आप यह देखने के लिए परीक्षण कर सकते हैं कि कोई चर विशेष रूप से अनसेट है (जैसा कि खाली स्ट्रिंग से अलग है):

if [[ -z ${variable+x} ]]

जहां "एक्स" मनमाने ढंग से है।

यदि आप जानना चाहते हैं कि कोई चर शून्य है लेकिन सेट नहीं है:

if [[ -z $variable && ${variable+x} ]]

227
2018-02-25 03:37



उस if [[ $variable ]] मेरे लिए ठीक काम किया, और इसकी भी आवश्यकता नहीं थी set -u यह एक अन्य प्रस्तावित समाधानों में से एक द्वारा आवश्यक था। - Teemu Leisti
मुझे लगता है कि यह स्वीकार किए गए उत्तर से बेहतर है। - qed
ऐसा करने पर आप गैर पोर्टेबल फीचर की सिफारिश क्यों कर रहे हैं? - Alastair Irvine
@AlastairIrvine: मैं अपने उत्तर की पहली वाक्य में पोर्टेबिलिटी का उल्लेख करता हूं, प्रश्न शीर्षक और शरीर में "बैश" शब्द होता है और सवाल टैग किया जाता है दे घुमा के, और डबल ब्रैकेट संरचना प्रदान करता है स्पष्ट फायदे कई मायनों में। और मैं स्थिरता और रखरखाव के कारणों के लिए मिश्रण ब्रैकेट शैलियों की अनुशंसा नहीं करता हूं। यदि आपको अधिकतम, सबसे कम आम denominator पोर्टेबिलिटी की आवश्यकता है, तो उपयोग करें sh बैश के बजाय। यदि आपको प्रदान की गई क्षमताओं की आवश्यकता है, तो बैश का उपयोग करें और इसे पूरी तरह से उपयोग करें। - Dennis Williamson
@ ब्रूनोब्रोनोस्की: मैंने संपादन को वापस कर दिया। इसके लिए कोई आवश्यकता नहीं है ; अतं मै। then बिना अर्धविराम के अगली पंक्ति पर हो सकता है। - Dennis Williamson


बैश (और कोई भी POSIX- संगत खोल) में एक चर तीन राज्यों में से एक में हो सकता है:

  • सेट नहीं
  • खाली स्ट्रिंग पर सेट करें
  • एक गैर खाली स्ट्रिंग पर सेट करें

अधिकांश समय आपको केवल यह जानने की आवश्यकता होती है कि कोई चर किसी रिक्त स्ट्रिंग पर सेट है या नहीं, लेकिन कभी-कभी अनसेट के बीच अंतर करना और खाली स्ट्रिंग पर सेट करना महत्वपूर्ण है।

निम्नलिखित उदाहरण हैं कि आप विभिन्न संभावनाओं का परीक्षण कैसे कर सकते हैं, और यह बैश या किसी भी POSIX- संगत शैल में काम करता है:

if [ -z "${VAR}" ]; then
    echo "VAR is unset or set to the empty string"
fi
if [ -z "${VAR+set}" ]; then
    echo "VAR is unset"
fi
if [ -z "${VAR-unset}" ]; then
    echo "VAR is set to the empty string"
fi
if [ -n "${VAR}" ]; then
    echo "VAR is set to a non-empty string"
fi
if [ -n "${VAR+set}" ]; then
    echo "VAR is set, possibly to the empty string"
fi
if [ -n "${VAR-unset}" ]; then
    echo "VAR is either unset or set to a non-empty string"
fi

यहां एक ही बात है लेकिन आसान टेबल फॉर्म में:

                        +-------+-------+-----------+
                VAR is: | unset | empty | non-empty |
+-----------------------+-------+-------+-----------+
| [ -z "${VAR}" ]       | true  | true  | false     |
| [ -z "${VAR+set}" ]   | true  | false | false     |
| [ -z "${VAR-unset}" ] | false | true  | false     |
| [ -n "${VAR}" ]       | false | false | true      |
| [ -n "${VAR+set}" ]   | false | true  | true      |
| [ -n "${VAR-unset}" ] | true  | false | true      |
+-----------------------+-------+-------+-----------+

${VAR+foo} निर्माण खाली स्ट्रिंग में फैलता है अगर VAR अनसेट या करने के लिए है foo अगर VAR कुछ भी सेट किया गया है (खाली स्ट्रिंग सहित)।

${VAR-foo} निर्माण के मूल्य में विस्तार VAR अगर सेट (खाली स्ट्रिंग पर सेट सहित) और foo अगर परेशान हो। यह उपयोगकर्ता-ओवरड्रेबल डिफ़ॉल्ट प्रदान करने के लिए उपयोगी है (उदा। ${COLOR-red} उपयोग करने के लिए कहते हैं red चरम जब तक COLOR कुछ पर सेट किया गया है)।

कारण क्यों [ x"${VAR}" = x ] अक्सर यह जांचने के लिए अनुशंसा की जाती है कि कोई चर या तो अनसेट या खाली स्ट्रिंग पर सेट है या नहीं, क्योंकि कुछ कार्यान्वयन [ आदेश (जिसे भी कहा जाता है test) छोटी गाड़ी हैं। अगर VAR कुछ ऐसा करने के लिए सेट है -n, तो दिए जाने पर कुछ कार्यान्वयन गलत चीज करेंगे [ "${VAR}" = "" ] क्योंकि पहली तर्क है [ गलत तरीके से व्याख्या की गई है -n ऑपरेटर, एक स्ट्रिंग नहीं।


205
2018-04-24 20:39



रिक्त स्ट्रिंग पर एक चर सेट के लिए परीक्षण भी किया जा सकता है [ -z "${VAR-set}" ]। - nwellnhof
@nwellnhof: धन्यवाद! मैंने ब्रीफ सिंटैक्स का उपयोग करने के लिए अपना जवाब अपडेट किया। - Richard Hansen
@ फेहेम मिठा: यह तुम्हारी गलती नहीं है - मेरा जवाब पढ़ना मुश्किल था। मैंने उम्मीदवार को उत्तर को और स्पष्ट करने के लिए एक टेबल जोड़ा। - Richard Hansen
@ रिचर्ड हान्सन: धन्यवाद, यह एक उपयोगी जोड़ है। - Faheem Mitha
अनसेट चेक विश्वसनीय नहीं हैं। अगर उपयोगकर्ता बुलाया जाता है set -u या set -o nounset बैश में, फिर परीक्षण केवल त्रुटि में होगा "bash: VAR: unbound variable"। देख stackoverflow.com/a/13864829 अधिक विश्वसनीय अनसेट जांच के लिए। मेरा चर-बारी है कि कोई चर शून्य या अनसेट है या नहीं [ -z "${VAR:-}" ]। मेरा चर यह है कि कोई चर खाली नहीं है या नहीं [ "${VAR:-}" ]। - Kevin Jin


-z एक सबसे अच्छा तरीका है।

मैंने उपयोग किए गए एक और विकल्प को एक चर सेट करना है, लेकिन इसे किसी अन्य चर द्वारा ओवरराइड किया जा सकता है

export PORT=${MY_PORT:-5432}

अगर $MY_PORT परिवर्तनीय खाली है, तो PORT 5432 पर सेट हो जाता है, अन्यथा पोर्ट को मूल्य के लिए सेट किया जाता है MY_PORT। नोट वाक्यविन्यास में कॉलन और डैश शामिल हैं।


36
2018-06-11 13:19



आकस्मिक रूप से आज यह पाया, और यह वही था जो मैं चाहता था। धन्यवाद! मुझे सहन करना है set -o nounset कुछ स्क्रिप्ट में। - opello


यदि आप सेट-रिक्त बनाम अनसेट स्थिति के मामलों को अलग करने में रुचि रखते हैं, तो bash के लिए -u विकल्प देखें:

$ set -u
$ echo $BAR
bash: BAR: unbound variable
$ [ -z "$BAR" ] && echo true
bash: BAR: unbound variable
$ BAR=""
$ echo $BAR

$ [ -z "$BAR" ] && echo true
true

24
2018-05-12 18:21





एक वैकल्पिक मैंने देखा है [ -z "$foo" ] निम्नलिखित है, हालांकि मुझे यकीन नहीं है कि लोग इस विधि का उपयोग क्यों करते हैं, किसी को भी पता है?

[ "x${foo}" = "x" ]

वैसे भी अगर आप अनसेट वैरिएबल को अस्वीकार कर रहे हैं (या तो द्वारा set -u या set -o nounset), तो आप उन दोनों तरीकों से परेशानी में भाग लेंगे। इसके लिए एक आसान फिक्स है:

[ -z "${foo:-}" ]

नोट: यह आपके परिवर्तनीय undef छोड़ देगा।


8
2017-10-20 03:58



विकल्प के बारे में एक टिप्पणी है -z पर pubs.opengroup.org/onlinepubs/009695399/utilities/test.html। असल में, यह एक विकल्प होने का मतलब नहीं है -z। इसके बजाय, यह मामलों को संभालती है $foo मेटाएक्टेक्टर के साथ शुरू होने वाली किसी चीज में विस्तार हो सकता है [ या test द्वारा भ्रमित किया जाएगा। शुरुआत में एक मनमाना गैर-मेटाएक्टेक्टर डालने से वह संभावना समाप्त हो जाती है। - James Sneeringer


सवाल पूछता है यह जांचने के लिए कि कोई चर एक खाली स्ट्रिंग है या नहीं और इसके लिए सबसे अच्छे उत्तर पहले से ही दिए गए हैं।
लेकिन मैं PHP में प्रोग्रामिंग उत्तीर्ण होने के बाद यहां पहुंचा और जो वास्तव में खोज रहा था वह एक चेक था PHP में खाली समारोह एक बैश खोल में काम कर रहा है।
जवाब पढ़ने के बाद मुझे एहसास हुआ कि मैं बैश में ठीक से सोच नहीं रहा था, लेकिन किसी भी तरह उस समारोह में एक समारोह खाली php में मेरे बैश कोड में soooo आसान हो गया होगा।
जैसा कि मुझे लगता है कि यह दूसरों के साथ हो सकता है, मैंने बैप में PHP खाली फ़ंक्शन को कनवर्ट करने का निर्णय लिया

के अनुसार PHP मैनुअल:
एक चर को खाली माना जाता है यदि यह अस्तित्व में नहीं है या यदि इसका मान निम्न में से एक है:

  • "" (एक खाली स्ट्रिंग)
  • 0 (0 पूर्णांक के रूप में)
  • 0.0 (0 फ्लोट के रूप में)
  • "0" (0 स्ट्रिंग के रूप में)
  • एक खाली सरणी
  • एक चर घोषित, लेकिन एक मूल्य के बिना

बेशक शून्य तथा असत्य मामलों को बाश में परिवर्तित नहीं किया जा सकता है, इसलिए उन्हें छोड़ दिया जाता है।

function empty
{
    local var="$1"

    # Return true if:
    # 1.    var is a null string ("" as empty string)
    # 2.    a non set variable is passed
    # 3.    a declared variable or array but without a value is passed
    # 4.    an empty array is passed
    if test -z "$var"
    then
        [[ $( echo "1" ) ]]
        return

    # Return true if var is zero (0 as an integer or "0" as a string)
    elif [ "$var" == 0 2> /dev/null ]
    then
        [[ $( echo "1" ) ]]
        return

    # Return true if var is 0.0 (0 as a float)
    elif [ "$var" == 0.0 2> /dev/null ]
    then
        [[ $( echo "1" ) ]]
        return
    fi

    [[ $( echo "" ) ]]
}



उपयोग का उदाहरण:

if empty "${var}"
    then
        echo "empty"
    else
        echo "not empty"
fi



डेमो:
निम्नलिखित स्निपेट:

#!/bin/bash

vars=(
    ""
    0
    0.0
    "0"
    1
    "string"
    " "
)

for (( i=0; i<${#vars[@]}; i++ ))
do
    var="${vars[$i]}"

    if empty "${var}"
        then
            what="empty"
        else
            what="not empty"
    fi
    echo "VAR \"$var\" is $what"
done

exit

आउटपुट:

VAR "" is empty
VAR "0" is empty
VAR "0.0" is empty
VAR "0" is empty
VAR "1" is not empty
VAR "string" is not empty
VAR " " is not empty

यह कहकर कि एक झटके तर्क में इस फ़ंक्शन में शून्य पर चेक साइड समस्याएं पैदा कर सकते हैं, इस फ़ंक्शन का उपयोग करने वाले किसी भी व्यक्ति को इस जोखिम का मूल्यांकन करना चाहिए और शायद उन चेक को केवल पहले को छोड़ने का निर्णय लेना चाहिए।


6
2017-08-31 20:11



समारोह के अंदर empty - तुमने क्यों लिखा [[ $( echo "1" ) ]] ; return बस के बजाय return 1 ? - Dor


पूरे अगर-तो और -z अनावश्यक हैं।

["$ foo"] & echo "foo खाली नहीं है"
["$ foo"] || गूंज "फू वास्तव में खाली है"

5
2018-01-26 14:02



अगर फू में केवल रिक्त स्थान होते हैं तो यह असफल हो जाएगा - Brian
अगर कुछ गोले में भी असफल हो जाएंगे foo एक डैश के साथ शुरू होता है क्योंकि इसे एक विकल्प के रूप में व्याख्या किया जाता है। जैसे सौर पर क्ष, zsh तथा दे घुमा के कोई समस्या नहीं है, श तथा / Bin / परीक्षण असफल हो जायेगी - ktf


यह सच है जब $ FOO सेट और खाली होता है:

[ "${FOO+x}" = x ] && [ -z "$FOO" ]

4
2018-05-20 20:52





जांचने के लिए व्यक्तिगत रूप से अधिक स्पष्ट तरीका पसंद करते हैं:

if [ "${VARIABLE}" == "" ]; then
  echo VARIABLE is empty
else
  echo VARIABLE is not empty
fi

4
2017-12-09 15:15



कुछ गोले डबल बराबर चिह्न स्वीकार नहीं करते हैं। - Dennis Williamson
सवाल बाश के बारे में था। मैं बैश का उपयोग कर रहा हूँ। मेरे लिए अच्छा काम करता है। आप वास्तव में किस बारे में बात कर रहे हैं? - Fedir RYKHTIK
यदि आप बैश का उपयोग कर रहे हैं, तो आपको डबल स्क्वायर ब्रैकेट का उपयोग करना चाहिए। मेरी पिछली टिप्पणी उन लोगों के लिए तथ्य का एक सरल बयान था जो आपके उत्तर को पढ़ सकते हैं और एक अलग खोल का उपयोग कर सकते हैं। - Dennis Williamson
इस मामले में सिंगल स्क्वायर ब्रैकेट ठीक है, कृपया देखें serverfault.com/questions/52034/... - Luca Borrione