2011-09-12 15 views
11
dpkg --list |grep linux-image |grep "ii " | while read line 
do 
    arr=(${line}) 
    let i=i+1 
    _constr+="${arr[2]} " 
done 
echo $i 
echo ${_constr} 

लूप के बाहर गूंज विवरण अपेक्षित चर प्रदर्शित नहीं करते हैं। मुझे लूप के बाहर परिवर्तनीय प्रचार की सामग्री कैसे बनाना चाहिए?बैश - लूप के बाहर परिवर्तनीय मान का प्रचार

+6

ध्यान रखें कि 'while' लूप एक अलग प्रक्रिया में चलता है, यही कारण है कि आप बदले गए चर नहीं देखते हैं। –

+1

प्रक्रिया प्रतिस्थापन का उपयोग करें? –

उत्तर

19

समस्या पाइप है, लूप नहीं। इसे इस तरह से आजमाएं

let i=0 
declare -a arr 

while read -r line ; do 
    arr=(${line}) 
    let i=i+1 
    _constr+="${arr[2]} " 
done < <(dpkg --list |grep linux-image |grep "ii ") 

echo $i 
echo ${_constr} 

आपको ऊपर दिखाए गए अनुसार स्पष्टता के लिए ग्लोबल्स को पूर्व घोषित करना चाहिए।

पाइप्स को सबहेल में निष्पादित किया जाता है, जैसा कि उनकी टिप्पणी में ब्लैगोवेस्ट ने उल्लेख किया था। process substitution instead का उपयोग करना (यह < <(commands) वाक्यविन्यास है) सब कुछ एक ही प्रक्रिया में रखता है, इसलिए वैश्विक चर में परिवर्तन संभव है।

संयोग से, अपने पाइप लाइन के साथ-साथ grep की

dpkg --list |grep '^ii.*linux-image' 

एक कम मंगलाचरण के बारे में चिंता करने के लिए सुधार किया जा सकता।

+0

ग्रेट स्पष्टीकरण। +1 –

+0

स्पष्टीकरण के लिए धन्यवाद :-) – masuch

+0

बैश 3.x में, लूप की आखिरी पंक्ति 'किया गया <<< \ 'आदेश \' ' – Ida

3

यह कुछ हद तक अपने प्रश्न द्वारा गुजरता है (और यह एक अच्छा सवाल है), लेकिन आप बस का उपयोग कर एक ही परिणाम प्राप्त कर सकते हैं:

_constr=($(dpkg --list | awk '/^ii.*linux-image/{print $2}')) 

($(cmd)) निर्माण के भीतर आदेश के उत्पादन का उपयोग कर एक बैश सरणी initialises ।

[[email protected]]$ echo ${_constr[*]} 
linux-image-2.6.35-22-generic linux-image-2.6.35-28-generic linux-image-generic 
[[email protected]]$ echo ${_constr[2]} 
linux-image-generic 

और आप ${#_constr[*]} का उपयोग कर तत्वों की संख्या प्राप्त कर सकते हैं।

[[email protected]]$ echo ${#_constr[*]} 
3 
+0

से ऊपर कोई स्थान नहीं बहुत धन्यवाद :-) – masuch

+0

यह वास्तव में ऐसा करने का सही तरीका है। मेरे पास परीक्षण करने के लिए डेबियन बॉक्स नहीं था या मैंने वही बात सुझाई होगी। – Sorpigal

0

वैकल्पिक रूप से, आप subshell अंदर गूंज बयान स्थानांतरित कर सकते हैं:

dpkg --list |grep linux-image |grep "ii " | (
    let i=0 
    declare -a arr 

    while read line 
    do 
    arr=(${line}) 
    let i=i+1 
    _constr+="${arr[2]} " 
    done 
    echo $i 
    echo ${_constr} 
) 

नोट कोष्ठक की प्रविष्टि को स्पष्ट रूप से परिभाषित करने के लिए जहां subshell शुरू होता है और समाप्त होता है।

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