$ PATH में पथों को अलग से कैसे प्रदर्शित किया जाए


45

मैं यह पता नहीं लगा सकता कि विभिन्न पथों को $PATHअलग-अलग कैसे सूचीबद्ध किया जाए ताकि वे इस तरह दिखें:

/bin
/usr/bin
/usr/local/bin

आदि।

क्या किसी को इसके लिए सही चर पता है?


प्रत्येक पथ एक अलग लाइन पर होना चाहिए
हांक

यदि आपके रास्तों में नई सुर्खियाँ हों तो क्या छापना चाहिए?
मार्टिअन


क्रॉस साइट डुप्लिकेट unix.stackexchange.com/q/80151/85039
सर्गी Kolodyazhnyy

जवाबों:


57

कोशिश करें sed:

$ sed 's/:/\n/g' <<< "$PATH"

या tr:

$ tr ':' '\n' <<< "$PATH"

या python:

$ python2 -c "import os; print os.environ['PATH'].replace(':', '\n')"

यहां उपरोक्त सभी :नई लाइनों के साथ सभी घटनाओं को प्रतिस्थापित करेंगे \n


अपने अजगर दृष्टिकोण पर भिन्नता:python -c 'import sys;print sys.argv[1].replace(":","\n")' $PATH
सर्जियो कोलोडियाज़नी

एक और अजगर भिन्नता, थोड़े हैकी: python -c "print r'$PATH'.replace(':', '\n')"(बैकस्लैश के मामले में एक कच्चे तार का उपयोग करके)
wjandrea

3
trमेरे लिए काम किया (मैक पर, btw)। धन्यवाद।
माइक एस।

उन लोगों के लिए, मेरे जैसे, जो इसे अपने साथ जोड़ना चाहते हैं .bash_profile, इसे इस तरह जोड़ें:alias path='tr ":" "\n" <<< "$PATH"'
माइक एस।

63

बैश के पैरामीटर विस्तार का उपयोग करें :

echo "${PATH//:/$'\n'}"

यह सभी :को $PATHएक नई पंक्ति ( \n) के द्वारा प्रतिस्थापित करता है और परिणाम को प्रिंट करता है। $PATHअपरिवर्तित रहता है की सामग्री ।
यदि आप केवल पहला बदलना चाहते हैं :, तो दूसरा स्लैश हटा दें:echo -e "${PATH/:/\n}"


3
मुझे लगता है कि यह सबसे अच्छा समाधान है क्योंकि यह शुद्ध बैश में किया जाता है ।
ryanmjacobs

1
@ryanmjacobs हल्के से जिज्ञासु: आपको क्या लगता है कि मेरा समाधान क्या उपयोग करता है? : D
मुरु

1
कृपया बताएं कि यह कैसे काम करता है।
ट्यूलेंस कोरडोवा

उस तरह के ऑपरेशन को क्या कहा जाता है? यह sed के समान है लेकिन यह sed नहीं है। इसका नाम क्या है इसलिए मैं इसके बारे में अधिक जानकारी के लिए वेब पर खोज कर सकता हूं।
ट्यूलेंस कोर्डोवा

3
मेरे उत्तर में लिंक (पैरामीटर विस्तार) का पालन करें और नीचे अंतिम दूसरे खंड तक स्क्रॉल करें:${parameter/pattern/string}
साइरस

27

IFS का उपयोग करना:

(set -f; IFS=:; printf "%s\n" $PATH)

IFS, वर्ण, जिस पर पार्टी बंटवारे करता है रखती है तो एक IFSसाथ :बनाता है बैश के विस्तार विभाजित $PATHपर :printfजब तक तर्क समाप्त नहीं हो जाते, तब तक प्रारूप स्ट्रिंग पर तर्क खो देता है। हमें ग्लोबिंग (वाइल्डकार्ड विस्तार) को अक्षम करने की आवश्यकता है set -fताकि पैटह निर्देशिका नामों में वाइल्डकार्ड का विस्तार न हो।


2
यह बैकस्लैश और रिक्त स्थान के साथ सही ढंग से काम करता है!
हेनरिक

14

का उपयोग कर xargs:

xargs -n1 -d: <<< $PATH

से man xargs

-n max-args
          Use  at  most  max-args  arguments per command line.

 -d delim
          Input  items  are terminated by the specified character.

इस पर भिन्नता, जैसे कि echo $PATH | xargs -n1 -d: echoबेमानी होगी या इससे कोई फर्क नहीं पड़ता?
सर्गी कोलोडियाज़नी

@ शेर आपके echo $PATH | xargs -n1 -d: लिए एक ही काम करेंगे लेकिन आप एक और शेल का इस्तेमाल करेंगे। पहले echo $PATHवाले बाकी का मूल्यांकन करने के लिए अगले शेल के लिए मूल्यांकन और पाइप आउटपुट करेंगे ।
स्मारिका

7

यहाँ गो में बराबर है:

$ cat path.go
package main

import (
    "fmt"
    "os"
    "strings"
)

func main() {
    for _, p := range strings.Split(os.Getenv("PATH"), ":") {
        fmt.Println(p)
    }
}

$ go run path.go
/usr/local/sbin
/usr/local/bin
/usr/sbin
/usr/bin
/sbin
/bin
/usr/games
/usr/local/games
/snap/bin
/home/nathan/.local/bin
/home/nathan/go/bin

7

यहाँ कुछ और दृष्टिकोण हैं। मैं एक PATHनिर्देशिका का उपयोग कर रहा हूं जिसमें बैकस्लैश, रिक्त स्थान और यहां तक ​​कि एक नई पंक्ति है जो यह दर्शाने के लिए है कि उन्हें किसी भी चीज के साथ काम करना चाहिए ( cutएक को छोड़कर जो नए सिरे से विफल रहता है):

$ echo "$PATH"
/bin:usr/bin/:/usr/local/bin:/some\ horrible thing:/even 
new lines
  • कुछ पर्ल तरीके:

    $ perl -pe 's/:/\n/g' <<<"$PATH"
    /bin
    usr/bin/
    /usr/local/bin
    /some\ horrible thing
    /even 
    new lines

    -pइसका मतलब है "स्क्रिप्ट द्वारा दिए गए आवेदन करने के बाद हर इनपुट लाइन मुद्रित -e"। स्क्रिप्ट प्रतिस्थापन ऑपरेटर ( s/oldnew/) का उपयोग कर रहा है ताकि सभी :को नई कहानियों के साथ बदल दिया जा सके ।

    $ perl -lne 'print for split /:/' <<<"$PATH"
    /bin
    usr/bin/
    /usr/local/bin
    /some\ horrible thing
    /even 
    new lines

    -lप्रत्येक के लिए एक नई पंक्ति कहते हैं printकॉल। यहाँ, स्क्रिप्ट इसके इनपुट को विभाजित कर रही है :और फिर प्रत्येक विभाजन तत्व पर लूप करती है और इसे प्रिंट करती है।

    $ perl -F: -ane '$"="\n";print "@F"' <<<"$PATH"
    /bin
    usr/bin/
    /usr/local/bin
    /some\ horrible thing
    /even 
    new lines

    -aबनाता है perlकी तरह व्यवहार awk: यह द्वारा दिए गए चरित्र पर अपने इनपुट पंक्तियों में से प्रत्येक बंट जाएगा -F(ताकि :, यहाँ) और सरणी में परिणाम को बचाने @F$"एक विशेष पर्ल चर, "सूची विभाजक", जिसका मूल्य एक मुद्रित सूची के प्रत्येक तत्व के बीच मुद्रित किया जाता है। इसलिए इसे एक नई पंक्ति में सेट करने से print @listप्रत्येक तत्व प्रिंट हो जाएगा @listऔर फिर एक नई रेखा। यहां, हम इसे प्रिंट करने के लिए उपयोग कर रहे हैं @F

    $ perl -F: -ane 'print join "\n", @F' <<<"$PATH"
    /bin
    usr/bin/
    /usr/local/bin
    /some\ horrible thing
    /even 
    new lines

    ऊपर के रूप में एक ही विचार, बस कम गोल्फ। उपयोग करने के बजाय $", हम स्पष्ट रूप joinसे सरणी को newlines और फिर मुद्रण के साथ जोड़ रहे हैं ।

  • grepPCRE जादू के साथ सरल :

    $ grep -oP '(^|:)\K[^:]+' <<<"$PATH"
    /bin
    usr/bin/
    /usr/local/bin
    /some\ horrible thing
    /even 
    new lines

    -oबनाता है grep, प्रत्येक पंक्ति का केवल मिलान भाग प्रिंट इसलिए प्रत्येक मैच एक अलग लाइन पर मुद्रित किया जाता है। -Pपर्ल कम्पैटिबल रेगुलर एक्सप्रेशन (PCRE) सक्षम बनाता है। रेगेक्स नॉन- :( [^:]+) के स्ट्रेच की तलाश कर रहा है जो कि लाइन की शुरुआत ^या ( या :कैरेक्टर ) का अनुसरण करता है। \Kएक PCRE चाल "इस बिंदु से पहले मिलान किया छोड़ें कुछ भी" है कि साधन और मुद्रण से बचने के लिए यहां इस्तेमाल किया जाता है :के रूप में अच्छी तरह से।

  • और एक cutसमाधान (यह एक नई सीमा पर विफल रहता है, लेकिन बैकस्लैश और रिक्त स्थान से निपट सकता है):

    $ cut -d: -f 1- --output-delimiter=$'\n' <<<"$PATH"
    /bin
    usr/bin/
    /usr/local/bin
    /some\ horrible thing
    /even 
    new lines

    उपयोग किए जाने वाले विकल्प हैं -d:जो इनपुट सीमांकक को सेट करते हैं :, -f 1-जिसका अर्थ है कि सभी फ़ील्ड (पहली से अंत तक) प्रिंट करें और --output-delimiter=$'\n'जो सेट करें, ठीक है, आउटपुट सीमांकक। $'\n'है एएनएसआई सी के हवाले से और एक तरह से खोल में एक नई पंक्ति चरित्र मुद्रित करने के लिए है।

उपरोक्त सभी उदाहरणों में, मैं प्रोग्राम के इनपुट के रूप में स्ट्रिंग को पास करने के लिए यहाँ स्ट्रिंग ( <<<) और स्ट्रिंग ( ) संचालक का उपयोग कर रहा हूँ । तो command <<<"foo"के बराबर है echo -n "foo" | command। ध्यान दें कि मैं हमेशा उद्धृत कर रहा हूं "$PATH", उद्धरणों के बिना, शेल ने न्यूलाइन वर्ण खाया होगा।


@ 7stud ने टिप्पणियों में एक और दृष्टिकोण दिया, जिसमें शामिल न करना बहुत अच्छा है:

$ perl -0x3a -l012 -pe '' <<<"$PATH"

यही गोल्फिंग के रूप में जाना जाता है । -0एक अष्टाधारी या हेक्साडेसिमल संख्या के रूप में इनपुट रिकॉर्ड विभाजक निर्दिष्ट करता है। यह वह है जो एक "लाइन" को परिभाषित करता है और इसका डिफ़ॉल्ट मान \n, एक नई लाइन वर्ण है। यहाँ, हम यह एक करने के लिए स्थापित कर रहे हैं :जो है x3aमें हेक्स (कोशिश printf '\x3a\n')। -lतीन काम करता है। पहले यह $/प्रत्येक पंक्ति के अंत से इनपुट रिकॉर्ड सेपरेटर ( ) को हटाता है - प्रभावी रूप से :यहां से हटा रहा है और दूसरा, यह आउटपुट रिकॉर्ड सेपरेटर ( $\) को जो भी ऑक्टल या हेक्स मान देता है ( 012है \n) सेट करता है। यदि $\इसे परिभाषित किया जाता है, तो इसे प्रत्येक printकॉल के अंत में जोड़ा जाता है , इसलिए यह प्रत्येक के लिए एक नई पंक्ति में परिणत होगा print

-peइच्छा पी स्क्रिप्ट द्वारा दिए गए आवेदन करने के बाद प्रत्येक इनपुट लाइन प्रिंट करें -e। यहाँ कोई स्क्रिप्ट नहीं है क्योंकि सभी काम ऊपर बताये गए विकल्प के झंडे से होते हैं!


आपके पर्ल वन लाइनर्स पर्याप्त अस्पष्ट नहीं हैं! यहाँ एक संस्करण है जहाँ -E स्विच को निष्पादित करने के लिए कोई कोड नहीं है क्योंकि अन्य स्विच सब कुछ संभालते हैं perl -0x3a -l012 -pe '' <<<$PATH:। स्पष्टीकरण: -0इनपुट रिकॉर्ड विभाजक सेट करता है (हेक्स / ऑक्टल नोटेशन में निर्दिष्ट है, एक्स 3 ए एक बृहदान्त्र है), -lदो चीजें करता है: 1) यह इनपुट रिकॉर्ड विभाजक को काटता है , 2) यह आउटपुट रिकॉर्ड विभाजक सेट करता है यदि कोई निर्दिष्ट है (ऑक्टल नोटेशन में) , 012 एक नई लाइन है)। एक -pलूप $ _ के मूल्य को प्रिंट करता है, जो प्रत्येक पंक्ति में पढ़ा जाएगा ।
7stud

यह भी ध्यान दें कि आपके उदाहरणों का उपयोग करके झंडे और झंडों -Fको समाप्त किया जा सकता है , जैसे -F स्वचालित रूप से उन को चालू करता है :। पर्लुन देखें । अच्छे उदाहरण हैं। -a-nperl -F: -e 'print(join "\n", @F);' <<<$PATH
7stud

@ 7stud वाह, यह वास्तव में शानदार है, धन्यवाद! बेशर्मी से चुराया और मेरे जवाब में जोड़ा (मुझे लगता है कि आप बुरा नहीं मानते हैं, बेझिझक इसे एक उत्तर के रूप में पोस्ट करें और मैं इसे हटा दूंगा)। और -Fजानकारी के लिए धन्यवाद । मैं वर्षों से -Fसंयुक्त रूप से उपयोग कर -anरहा हूं, मुझे कभी इस बात का एहसास नहीं हुआ कि दूसरों को निहित किया गया है। वैसे, मैंने देखा कि सर्ग ने कोड गोल्फ का उल्लेख किया है , लेकिन मुझे लगता है कि यदि आप इस प्रकार की चीज़ में हैं तो आप यूनिक्स और लिनक्स का भी आनंद लेंगे ।
terdon

धन्यवाद। इस कथन के बारे में एक स्पष्टीकरण: अंत में, -lप्रत्येक प्रिंट कॉल के अंत में दिए गए आउटपुट रिकॉर्ड विभाजक को भी जोड़ता है। वास्तव में, प्रिंट हमेशा आउटपुट रिकॉर्ड विभाजक को जोड़ता है $/, एक स्ट्रिंग के अंत तक - यदि आउटपुट रिकॉर्ड विभाजक परिभाषित किया गया है। डिफ़ॉल्ट रूप से यह अपरिभाषित है। तो -lजूस सेट करता है $/, और यह स्ट्रिंग के अंत में नईलाइन जोड़ने के लिए प्रिंट का कारण बनता है।
7stud

मुझे लगता है कि आप बुरा नहीं मानते - बिल्कुल नहीं। :)
7stud

6

इस उत्तर में:

  1. सी
  2. अजगर
  3. माणिक
  4. वैकल्पिक जाग

1. सी

चूंकि सभी स्क्रिप्टिंग भाषाओं को पहले ही ले लिया गया है, मैं सी के साथ जाऊंगा। get_env()फ़ंक्शन के साथ पर्यावरण चर प्राप्त करना काफी आसान है ( जीएनयू सीबीएस प्रलेखन देखें )। बाकी बस चरित्र हेरफेर है

bash-4.3$ cat get_path.c
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main()
{
    char *path = getenv("PATH");
    int length = strlen(path) -1;
    for(int i=0;i<=length;i++){
        if (path[i] == ':')
            path[i] = '\n';
        printf("%c",path[i]);
    }
    printf("\n");
    return 0;
}
bash-4.3$ gcc get_path.c
bash-4.3$ ./a.out 
/home/xieerqi/bin
/usr/local/sbin
/usr/local/bin
/usr/sbin
/usr/bin
/sbin
/bin
/usr/games
/usr/local/games
/snap/bin
/opt/microchip/xc16/v1.25/bin
/opt/microchip/xc32/v1.40/bin
/opt/microchip/xc8/v1.35/bin
/home/xieerqi/bin
/home/xieerqi/bin/sh

2. अजगर

लेकिन यह भी क्योंकि "क्यों नहीं", यहाँ कमांड लाइन तर्क के माध्यम से वैकल्पिक पायथन संस्करण है sys.argv

python -c 'import sys; print "\n".join(sys.argv[1].split(":"))' "$PATH"

3. माणिक

रूबी सी संकलक और पायथन दुभाषिया के विपरीत, डिफ़ॉल्ट रूप से उबंटू के साथ नहीं आती है, लेकिन अगर आप कभी भी इसका उपयोग करते हुए खुद को पाते हैं, तो रूबी में समाधान यह होगा:

ruby -ne 'puts $_.split(":")' <<< "$PATH"

जैसा कि टिप्पणियों में 7stud (बहुत-बहुत धन्यवाद!) द्वारा सुझाया गया है , इसे भी छोटा किया जा सकता है

ruby -F: -ane 'puts $F' <<<$PATH

और इस तरह से

ruby -0072 -ne 'puts chomp' <<<$PATH

4. वैकल्पिक awk

हम split()सरणी में पढ़ी गई लाइन को तोड़ने के लिए फ़ंक्शन का उपयोग कर सकते हैं, और for-eachप्रत्येक आइटम को अलग लाइन पर प्रिंट करने के लिए लूप का उपयोग कर सकते हैं।

awk '{split($0,arr,":"); for(var in arr) print arr[var]}' <<< $PATH

1
अच्छा माणिक उदाहरण। putsस्वचालित रूप से एक सरणी के तत्वों को अलग-अलग लाइनों पर प्रिंट करता है! आप स्विच को विभाजित भी कर सकते हैं: ruby -F: -ane 'puts $F' <<<$PATH स्पष्टीकरण: निर्दिष्ट वर्ण पर -Fसेट करता $;है, जो स्ट्रिंग :: विभाजन ($ का उपयोग डिफ़ॉल्ट डिफ़ॉल्ट विभाजक है; शून्य का डिफ़ॉल्ट मान है, जो व्हाट्सएप पर विभाजित होता है)। -a$ _ को कॉल करता है। विभाजित करें, जहां $ _ एक लाइन में पढ़ा जाता है जो (हो जाता है) का उपयोग करता है और परिणामी सरणी को असाइन करता है $F
7stud

@ 7stud हे, धन्यवाद! :) वहाँ -Fध्वज का पता नहीं था - मैं बस रूबी के साथ शुरू कर रहा हूं, इसलिए चीजों को थोड़ा कच्चा तरीका है।
सर्गी कोलोडियाज़नी

नहीं, यह अस्पष्ट सामान है। आपका एक लाइनर बहुत ही पठनीय है, और स्पष्टता को हर बार संक्षिप्त रूप से स्वीकार करना चाहिए।
7stud

हा। मैं एक छोटे से पता लगा ruby -0072 -ne 'puts chomp' <<<$PATH:। स्पष्टीकरण: -0इनपुट रिकॉर्ड विभाजक सेट करता है (अष्टक प्रारूप में एक चरित्र निर्दिष्ट करें; 072 एक बृहदान्त्र है)। रूबी Perl के समान $ _ को नियोजित करती है। हो जाता है () विधि ( -nलूप में प्रयुक्त ) $ _ को उस मौजूदा लाइन पर सेट करता है जो अंदर पढ़ी जाती है। और chomp()बिना arg के, chomps + _ को सेट करता है। मुझे अब भी तुम्हारा साथ अच्छा लगता है। :)
7stud

@ 7stud वास्तव में, जिसे आपने पहले -Fध्वज के साथ पोस्ट किया था , वह छोटा है। यदि आप ऐसा करते हैं, तो echo "ruby -F: -ane 'puts $F' <<<$PATH" |wc -c मुझे लगता है कि यह 271, बाइट्स है, लेकिन अष्टक संख्या 276 है। यह पूरे कमांड के लिए है, अगर हम केवल कोड को ही puts $Fस्पष्ट रूप से छोटा मानते हैं । :) वैसे, क्या आप कोड गोल्फ के बारे में जानते हैं ? यह कम से कम बाइट्स में प्रोग्रामिंग पहेली के समाधान के लिए साइट है। इससे संबंधित एक प्रश्न है: codegolf.stackexchange.com/q/96334/55572
Sergiy Kolodyazhnyy

5

संभवतः एकमात्र तरीका जिसका उल्लेख नहीं किया गया है वह वह तरीका है जो मैं वर्षों से इसका उपयोग कर रहा हूं:

echo $PATH | tr ":" "\n"

इसलिए, आपके .profile या .bash_profile या जो भी हो, में आप जोड़ सकते हैं:

alias path='echo $PATH | tr ":" "\n"'


1
इस उत्तर ने पहले ही इसका उल्लेख कर दिया है ..
हेमायल

हाँ, लेकिन मुझे उपनाम के लिए सुझाव पसंद है।
7stud

4

हमें अधिक जावा की आवश्यकता है!

public class GetPathByLine {
    public static void main(String[] args) {
        for (String p : System.getenv("PATH").split(":")) {
            System.out.println(p);
        }
    }
}

इसे सहेजें GetPathByLine.java, और उपयोग करके संकलित करें:

javac GetPathByLine.java

साथ दौड़ो:

java GetPathByLine

┌─[17:06:55]─[kazwolfe@BlackHawk]
└──> ~ $ cat GetPathByLine.java 
public class GetPathByLine {
    public static void main(String[] args) {
        for (String p : System.getenv("PATH").split(":")) {
            System.out.println(p);
        }
    }
}
┌─[17:06:58]─[kazwolfe@BlackHawk]
└──> ~ $ javac GetPathByLine.java 
┌─[17:07:02]─[kazwolfe@BlackHawk]
└──> ~ $ java GetPathByLine 
/usr/local/sbin
/usr/local/bin
/usr/sbin
/usr/bin
/sbin
/bin
/usr/games
/usr/local/games
/snap/bin

वाह यह ओवरकिल है। आप इसे पायथन 3 में एक पंक्ति में कर सकते हैं:python3 -c "import os; [print(p) for p in os.getenv('PATH').split(':')]"
wjandrea

1
@wjandrea यह बात है! : डी
काज वोल्फ

3

जाग के माध्यम से।

echo $PATH | awk -F: '{for(i=1;i<=NF;i++)print $i}'

अजगर के माध्यम से।

$ echo $PATH | python3 -c 'import fileinput
for line in fileinput.input():
    for i in line.split(":"):
        print(i)'

ध्यान दें कि अजगर में इंडेंटेशन बहुत महत्वपूर्ण है।


शोर्टर अवेक:echo $PATH | awk '{gsub(/\:/,"\n");print}'
सर्जियो कोलोडियाज़नी

मुझे यकीन नहीं है कि आप परेशान क्यों होते हैं fileinputजब आप बस इस्तेमाल कर सकते हैं input:python3 -c 'print(*input().split(":"), sep="\n")' <<< "$PATH"
wjandrea

2

मैं स्टीफन कोलियर के "बैश पाथ फंक्शंस" का उपयोग करता हूं ( लिनक्स जर्नल में उनका लेख देखें )। यह मुझे शेल प्रोग्रामिंग में "कॉलन सेपरेटेड लिस्ट" को डेटाटाइप के रूप में उपयोग करने की अनुमति देता है। उदाहरण के लिए, मैं वर्तमान निर्देशिका की सभी निर्देशिकाओं की एक सूची तैयार कर सकता हूं:

dirs="";for i in * ; do if [ -d $i ] ; then addpath -p dirs $i; fi; done  

फिर, listpath -p dirsएक सूची बनाता है।


2

@ साइरस जवाब के लिए स्पष्टीकरण

echo "${PATH//:/$'\n'}"

टिप्पणियाँ:

ANSI-C कोटिंग - यह $ 'some \ ntext' की व्याख्या करता है

शेल पैरामीटर विस्तार - यह $ {पैरामीटर / पैटर्न / स्ट्रिंग} की व्याख्या करता है, यदि पैटर्न Exp / ’से शुरू होता है, तो पैटर्न के सभी मैच स्ट्रिंग से बदल दिए जाते हैं।

तो हमारे पास:

  1. एक पैटर्न /: जो सभी मैचों को बदलने के लिए '/' से शुरू होता है
  2. एक स्ट्रिंग $ '\ n' जिसे नई लाइन प्रतीक (\ n) के इलाज के लिए $ 'किसी भी' संकुचन के साथ उद्धृत किया गया है।

1

एक और AWK तरीका है कि हर डायरेक्टरी को एक अलग क्षेत्र के बजाय एक अलग रिकॉर्ड के रूप में माना जाए ।

awk 'BEGIN{RS=":"} {print $0}' <<<"$PATH"

मुझे लगता है कि वाक्यविन्यास विशेष रूप से सहज है। लेकिन, यदि आप चाहें, तो आप इसे संक्षिप्त बनाकर संक्षिप्त कर सकते हैं print $0(यह डिफ़ॉल्ट क्रिया है, और 1सत्य का मूल्यांकन करता है, जिससे यह हर पंक्ति के लिए किया जाता है):

awk 'BEGIN{RS=":"} 1' <<<"$PATH"

AWK का डिफ़ॉल्ट इनपुट और आउटपुट रिकॉर्ड सेपरेटर नई लाइन (लाइन ब्रेक) है। इनपुट पढ़ने के लिए इनपुट रिकॉर्ड सेपरेटर ( RS) सेट करने :से पहले, AWK स्वचालित रूप $PATHसे अपने संवैधानिक निर्देशिका नामों में एक कोलोन-सीमांकित को पार्स कर देता है । AWK $0प्रत्येक पूरे रिकॉर्ड में फैलता है, नईलाइन आउटपुट रिकॉर्ड विभाजक बनी हुई है , और कोई लूपिंग या gsubआवश्यक नहीं है।

ek@Io:~$ echo "$PATH"
/home/ek/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin
ek@Io:~$ awk 'BEGIN{RS=":"} {print $0}' <<<"$PATH"
/home/ek/bin
/usr/local/sbin
/usr/local/bin
/usr/sbin
/usr/bin
/sbin
/bin
/usr/games
/usr/local/games
/snap/bin

AWK का उपयोग अक्सर रिकॉर्ड को अलग-अलग क्षेत्रों में पार्स करने के लिए किया जाता है, लेकिन इसके लिए केवल निर्देशिका नामों की सूची बनाने की आवश्यकता नहीं होती है।

यह रिक्त स्थान (स्थान और टैब) युक्त इनपुट के लिए भी काम करता है, यहां तक ​​कि कई लगातार रिक्त स्थान भी:

ek@Io:~$ awk 'BEGIN{RS=":"} {print $0}' <<<$'ab\t\t c:de    fg:h'
ab               c
de    fg
h

यही है, जब तक कि आप AWK को रिकॉर्ड के पुनर्निर्माण का कारण नहीं बनाते हैं (नीचे देखें), इनपुट में रिक्त स्थान या टैब (डिफ़ॉल्ट फ़ील्ड विभाजक) होने की कोई समस्या नहीं है। आपके PATHशायद उबंटू प्रणाली पर स्थान नहीं है, लेकिन अगर यह होता है, तो भी यह काम करेगा।


यह ध्यान देने योग्य है, एक साइड नोट के रूप में, कि AWK एक फ़ील्ड के संग्रह के रूप में रिकॉर्ड की व्याख्या करने की क्षमता निर्देशिका घटकों की एक तालिका के निर्माण की संबंधित समस्या के लिए उपयोगी हो जाती है :

ek@Io:~$ awk -F/ 'BEGIN{RS=":"; OFS="\t"} {$1=$1; print $0}' <<<"$PATH"
        home    ek      bin
        usr     local   sbin
        usr     local   bin
        usr     sbin
        usr     bin
        sbin
        bin
        usr     games
        usr     local   games
        snap    bin

जिज्ञासु $1=$1असाइनमेंट AWK को रिकॉर्ड के पुनर्निर्माण के लिए मजबूर करने के उद्देश्य से कार्य करता है ।

(यह संभवतः उन मामलों के लिए अधिक उपयोगी है जहां घटकों पर अतिरिक्त प्रसंस्करण किया जाना है, केवल तालिका को प्रिंट करने के लिए दिखाए गए सटीक उदाहरण के लिए।)



0

$ PATH में पथों को अलग से कैसे प्रदर्शित किया जाए

ये मेरे संबंधित उपयोग-मामलों और संगतता और संसाधन उपयोग के बारे में चिंताओं के आधार पर ऐसा करने के मेरे पसंदीदा तरीके हैं।

tr

सबसे पहले, अगर आपको याद करने के लिए एक त्वरित, आसान और पठनीय समाधान की आवश्यकता है, तो बस कॉल करें PATHऔर इसे अनुवादtr करने के लिए ( ) कोलाइन्स में बदल दें:

echo $PATH | tr : "\n"

इसमें पाइप के कारण दो प्रक्रियाओं का उपयोग करने का नकारात्मक पक्ष है, लेकिन अगर हम सिर्फ एक टर्मिनल में हैकिंग कर रहे हैं, तो क्या हम वास्तव में इस बारे में परवाह करते हैं?

बैश का शेल पैरामीटर विस्तार

यदि आप .bashrcइंटरैक्टिव उपयोग के लिए अपने में एक स्थायी समाधान चाहते हैं, तो आप निम्न आदेश को अन्य नाम दे सकते हैं path, लेकिन इस समाधान की पठनीयता संदिग्ध है:

alias path="echo \"${PATH//:/$'\n'}\""

यदि पैटर्न '/' से शुरू होता है, तो पैटर्न के सभी मैचों को स्ट्रिंग के साथ बदल दिया जाता है। आम तौर पर केवल पहले मैच को बदल दिया जाता है।

उपरोक्त आदेश बैश के शेल पैरामीटर विस्तार का उपयोग करते हुए कोलन को न्यूलाइन्स के साथ प्रतिस्थापित करता है :

${parameter/pattern/string}

इसे समझाने के लिए:

          # v--v---------delimiters, a'la sed
echo "${PATH//:/$'\n'}"
          #  ^^ ^^^^^----string, $ required to get newline character.
          #   \----------pattern, / required to substitute for *every* :.

जब आप कमांड लाइन पर हैकिंग कर रहे हों तो सौभाग्य की बात है, अगर आपने इसे अलियास नहीं किया है, हालांकि।

IFS, बैश और डैश में परीक्षण किया गया

वैकल्पिक रूप से, एक काफी क्रॉस-संगत, पठनीय और समझने योग्य दृष्टिकोण जो शेल के अलावा किसी भी चीज़ पर भरोसा नहीं करता है, निम्नलिखित फ़ंक्शन का उपयोग करता है (मैं आपके सुझाव देता हूं .bashrc।)

निम्न फ़ंक्शन अस्थायी रूप से आंतरिक (या इनपुट) फ़ील्ड सेपरेटर (IFS) को एक कॉलोन बनाता है, और जब किसी सरणी को दिया जाता है printf, तो यह तब तक निष्पादित होता है जब तक कि सरणी का उपयोग नहीं किया जाता है:

path () {
    local IFS=:
    printf "%s\n" ${PATH}
    }

का यह तरीका समारोह निर्माण , IFSऔर printfके लिए POSIX द्वारा प्रदान की जाती है तो यह (के रूप में विशेष रूप से डैश, जो उबंटू आमतौर पर उपनाम सबसे POSIX तरह के गोले में काम करना चाहिए sh)।

अजगर

क्या आपको इसके लिए अजगर का उपयोग करना चाहिए? आप ऐसा कर सकते हैं। यह सबसे छोटा पायथन कमांड है जिसके बारे में मैं सोच सकता हूं:

python -c "print('\n'.join('${PATH}'.split(':')))"

या पायथन 3 केवल (और शायद अधिक पठनीय?):

python3 -c "print(*'${PATH}'.split(':'), sep='\n')"

ये किसी भी सामान्य शेल वातावरण में काम करना चाहिए, जब तक कि आपके पास पायथन है।


0

यह समाधान Java , C , go और awk समाधानों की तुलना में सरल है :

$ LPATH=$PATH wine cmd /c echo %LPATH::=$'\n'% 2> /dev/null
/usr/local/bin
/usr/local/sbin
/usr/bin
/usr/sbin

यहाँ एक और बड़ी संभावना है:

$ jrunscript -classpath /usr/share/java/bsh.jar -e 'print(java.lang.System.getenv("PATH").replaceAll(":","\n"))'
/usr/local/bin
/usr/local/sbin
/usr/bin
/usr/sbin

इसके लिए कुछ निर्भरताएँ स्थापित करनी होंगी:

sudo apt-get install openjdk-8-jdk-headless bsh
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.