क्या मैं बैश ग्लोब से केवल एक परिणाम का चयन कर सकता हूं?


14

मैं एक आउटपुट पर कुछ रिपोर्टिंग को स्वचालित करने के लिए काम के लिए एक स्क्रिप्ट लिखने की कोशिश कर रहा हूं। लॉग फाइलें इस प्रकार की पथ संरचना में संग्रहीत (वर्तमान में, इसे भविष्य में 'मानकीकृत' किया जा रहा है:

/<root_path>/<process_one_path>/logs/<time_date_stamp>/<specific_log_file>

/<root_path>/<process_two_path>/logs/<different_time_date_stamp>/<specific_log_file>

पथ का प्रत्येक भाग समय दिनांक टिकटों को छोड़कर जाना जाता है, जो हमेशा फ़ोल्डर में नवीनतम होते हैं।

अगर मैं टाइम डेट स्टैम्प के स्थान पर वाइल्ड कार्ड का उपयोग करने की कोशिश करता हूं, तो मुझे कई परिणाम मिलते हैं, जैसे:

> ls /<root_path>/<process_two_path>/logs/* [tab]
20130102-175103
20130118-090859
20130305-213506

मैं केवल यह चाहता हूं कि नवीनतम को लौटाएं, क्या यह बैश के साथ संभव है?

NB (मेरे पास zsh नहीं है, और जितना प्यारा मुझे लगता है मुझे संदेह है कि हम कभी भी इसे काम पर ले लेंगे)

जवाबों:


9

निम्नलिखित बाश में काम करता है 4.2:

list=( /<root_path>/<process_two_path>/logs/* )
echo "${list[-1]}"

यदि आपका बैश पुराना संस्करण है:

list=( /<root_path>/<process_two_path>/logs/* )
echo "${list[${#list[@]}-1]}"

यह निश्चित रूप से मेरे घर के कंप्यूटर पर काम करता है, लेकिन मैं गारंटी नहीं दे सकता कि यह काम पर काम करेगा?
प्यूरफेरेट

@Purefer जो भाग काम नहीं कर सकता है वह ऋणात्मक सरणी सूचकांक ( -1) है। इसे बैश 4.2 में जोड़ा गया था। आरएचईएल 5 संभवतया सबसे पुराना समर्थित मुख्यधारा उद्यम डिस्ट्रो उपलब्ध है और यह बैश 4.2.20 का उपयोग करता है।
पैट्रिक

1
पुराने संस्करण bashहैं: "${list[@]: -1}"जैसे ksh93(से [-1]आता है zsh)।
स्टीफन चेज़लस

@ पैट्रिक - RHEL5 बैश का उपयोग करता है 3.2। आरएचईएल 3 और 4 अभी भी विस्तारित जीवन के तहत समर्थित हैं।
जोर्डम

1
@Pureferret आप सरणी लंबाई के साथ अंकगणित भी कर सकते हैं, मेरा संपादन देखें।
गिल्स एसओ- बुराई को रोकना '

10

POSIXly:

 set -- /<root_path>/<process_two_path>/logs/*
 shift "$(($# - 1))"
 printf '%s\n' "$1"

चूंकि आप उल्लेख करते हैं zsh:

 print -r /<root_path>/<process_two_path>/logs/*([-1])

4

लूप के लिए एक बैश में बैश ग्लोब का उपयोग करें। ऐशे ही:

for filename in <logdir>/*; do :; done; echo "$filename"

यह इस तथ्य पर निर्भर करता है कि बैश ग्लोब विस्तार को वर्णानुक्रम में क्रमबद्ध करता है। अधिक जानकारी के लिए बैश मैनुअल पढ़ें । ध्यान दें कि यह LC_COLLATE पर निर्भर करता है । यह इस तथ्य पर भी निर्भर करता है कि filenameलूप समाप्त होने के बाद चर में अंतिम मूल्य अभी भी है।

यदि आप सबसे पुराने टाइमस्टैम्प के साथ फ़ाइल नाम चाहते हैं, तो आप इसे इस तरह से कर सकते हैं:

for filename in <logdir>/*; do echo "$filename"; break; done

1

-1 पाइपलाइनों में डिफ़ॉल्ट है, और एलएस आउटपुट पहले से ही हल किया जाना चाहिए:

ls | tail -n1

यदि अन्य लोग पहले या अंतिम परिणाम को अंतःक्रियात्मक रूप से सम्मिलित करने के तरीके की तलाश कर रहे थे, तो आप मेनू-पूर्ण या मेनू-पूर्ण-बैकवर्ड इन .inputrc को बाँध सकते हैं:

"\e\t": menu-complete
"\e[Z": menu-complete-backward # shift-tab

यदि शो-ऑल-इफ-एम्बिगुअस सक्षम है, set completion-query-items 0तो 101 या अधिक परिणाम होने पर प्रॉम्प्ट को हटा set page-completions offदेता है और पेजर को निष्क्रिय कर देता है।


-1
ls -tr | tail -1

चाल चलनी चाहिए।


3
ध्यान दें कि आपको आउटपुट को पार्स नहीं करना चाहिएls । कभी।
रहमू

ऐसा क्यों है? और यह ग्लोब से आउटपुट का उपयोग करने से कैसे भिन्न होता है?
स्लिपसेट

2
mywiki.wooledge.org/ParsingLs यह बताते हैं ...
फिसल
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.