स्क्रिप्ट में $ का उपयोग नहीं किया जा सकता है?


11

बस सोच रहा था कि यह काम क्यों नहीं कर रहा है

#!/bin/bash 

ls /bin
ls !$

मैं ls /binदो बार दौड़ने की उम्मीद करता हूं , लेकिन दूसरे ने त्रुटियों को उठाया जैसा !$कि व्याख्या नहीं किया गया था

क्या मुझे कुछ याद आया, या !$केवल कमांड लाइन में काम किया?

मुझे man bash(मैक पर) प्रासंगिक भाग नहीं मिला


9
हालांकि एक समाधान है क्या यह वास्तव में एक स्क्रिप्ट में इसे प्राप्त करने का सबसे अच्छा तरीका है? जब आप गैर-संवादात्मक रूप से चलते हैं तो इतिहास डिफ़ॉल्ट रूप से अक्षम होता है - एक लंबी स्क्रिप्ट .bash_history फ़ाइल को स्पैम करने जा रही है। यह कहते हुए कि यह पूछने लायक नहीं था, लेकिन अगर आप इसे स्क्रिप्ट में इस्तेमाल करने की सोच रहे हैं, तो क्या यह वास्तव में सबसे अच्छा तरीका है?
फ़्लुंगो

जवाबों:


26

इतिहास और इतिहास का विस्तार डिफ़ॉल्ट रूप से अक्षम होता है जब शेल गैर-अंतःक्रियात्मक रूप से चलता है।

आप की जरूरत है:

#!/bin/bash 

set -o history
set -o histexpand

ls /bin
ls !$

या:

SHELLOPTS=history:histexpand bash script.sh

यह सभी बैश उदाहरणों को प्रभावित करेगा जो script.shचल सकते हैं।


9
SHELLOPTS के साथ सावधान, यह प्रभावित करेगा कि bashचलाता है script.sh, लेकिन यह भी सभी अन्य bashउदाहरण है कि script.shअंततः चला सकते हैं (अन्य bashलिपियों की तरह ...)।
स्टीफन चेजेलस

और यह आपकी स्क्रिप्ट चलाने वाले किसी अन्य उदाहरण को प्रभावित नहीं करेगा । bash
ब्लैकलाइट शाइनिंग

मुझे लगता है कि @ StéphaneChazelas की टिप्पणी को इसमें संपादित किया जाए तो यह उत्तर सुधर जाएगा।
ओलिपहंट - मोनिका

7

करने के लिए समझदार बात होगी

ls /bin
ls $_

या

set ls /bin
$*
$*

या

c='ls /bin'
$c
$c

कैविट्स: यह याद रखने योग्य है कि इनमें से प्रत्येक कुछ नुकसान के साथ आता है। $ _ समाधान केवल अंतिम एकल तर्क को पकड़ता है: इसलिए ls foo bar$ _ युक्त छोड़ देगा bar। एक का उपयोग कर setतर्कों (को पार कर जाएगी $1, $2, आदि)। और ये सभी लिखित के रूप में काम करेंगे, लेकिन जब अधिक जटिल कमांड (जहां बचना और व्हाट्सएप मामला) के लिए सामान्यीकृत होता है, आप कुछ कठिनाइयों में भाग सकते हैं। उदाहरण के लिए: ls 'foo bar'(जहाँ एकल पथनाम तर्क foo barमें दो या दो से अधिक रिक्त स्थान होते हैं, या कोई अन्य व्हाट्सएप वर्ण) इन उदाहरणों में से किसी में भी सही ढंग से व्यवहार नहीं किया जा सकता है। उचित रूप से भागने (संभवतः एक evalकमांड के साथ संयुक्त ), या "$@"इसके बजाय का उपयोग करके $*, उन मामलों को प्राप्त करने के लिए आवश्यक हो सकता है।


1
एक जवाब के लिए +1 जो पोर्टेबल है और इंटरैक्टिव उपयोग को आसान बनाने के उद्देश्य से बशीवाद का दुरुपयोग नहीं करता है। (एक तरफ के रूप में, डिफ़ॉल्ट सेटअप में अंतःक्रियात्मक रूप से विस्मयबोधक चिह्न का विस्तार करने के लिए बैश की इच्छा कुछ ऐसा है जिसे मैं अन्य शेल के उपयोगकर्ता के रूप में काउंटरिंटुइवेट पाता हूं, और काउंटरप्रोडक्टिव है क्योंकि यह हमेशा मुझे डराता है जब मैं कुछ जटिल शेल कमांड करने की कोशिश कर रहा हूं)।
mtraceur

यद्यपि इस समय लिखा गया था, मैं इसे देने में संकोच कर रहा था क्योंकि शुरुआती शेल स्क्रिप्टर्स के मुद्दों के कारण यह संभव होगा जब इसे और अधिक जटिल आदेशों के लिए सामान्यीकृत करने की कोशिश की जाएगी। मैंने एक सुझाव दिया था कि कम से कम एक कैविटी पैराग्राफ जोड़ना संभव है, जिससे संभावित नुकसान हो सकता है।
mtraceur

@mtraceur: यह पोर्टेबल नहीं है, केवल bash, zsh, ksh (यदि दो कमांड एक ही लाइन में नहीं हैं) में काम करते हैं। पानी का छींटा, mksh में केवल जब इंटरैक्टिव
cuonglm

@cuongim: क्षमा करें, मैं शायद बहुत लापरवाह सामान्य था। $_जिस तरह से पोर्टेबल नहीं है, आप ठीक कह रहे हैं। setदृष्टिकोण गैर-सहभागी पानी का छींटा में काम करता है, और साथ ${1+"$@"}(प्लस ZSH वैश्विक उर्फ) चाल, सामान्य होना चाहिए, हालांकि मैं थोड़ा याद है कि setकुछ (पुराने?) के गोले के साथ पूरी तरह से पोर्टेबल नहीं किया जा रहा का एक इतिहास है। परिभाषित-ए-चर-होल्डिंग-ऑफ-द-कमांड-एंड-इवल-इट-एप्रोच, विशेष रूप से उचित भागने और एक वास्तविक evalआदेश का उपयोग करते हुए , आमतौर पर पूरी तरह से पोर्टेबल है जहां तक ​​मुझे पता है।
mtraceur
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.