पूंछ का उपयोग करते समय नई-नई सीमांकितों को परिवर्तित करें


20

मैं tailन्यूलाइन की बजाय अशक्त-समाप्त लाइनों का उपयोग करने के लिए आउटपुट कैसे बदल सकता हूं ?

मेरा प्रश्न इस के समान है: बैश में अशक्त-सीमांकित इनपुट पर `हेड` और` टेल` कैसे करें? , लेकिन इसमें अलग है कि मैं कुछ करना चाहता हूं:

tail -f myFile.txt | xargs -i0 myCmd {} "arg1" "arg2"

मैं उपयोग नहीं कर रहा हूँ find, और इसलिए उपयोग नहीं कर सकता-print0

यह सब xargs में होने वाली त्रुटि से बचने के लिए है:

xargs: unmatched double quote;
    by default quotes are special to xargs unless you use the -0 option

जवाबों:


26

यदि आप चाहते हैं कि अंतिम 10 लाइनें:

tail myFile.txt | tr '\n' '\0' | xargs -r0i myCmd {} arg1 arg2

लेकिन जीएनयू के साथ xargs, आप सीमांकक को नई रेखा के साथ सेट कर सकते हैं:

tail myFile.txt | xargs -ri -d '\n' myCmd {} arg1 arg2

(के -0लिए कम है -d '\0')।

आंशिक रूप से, आप भी हर चरित्र से बच सकते हैं:

tail myFile.txt | sed 's/./\\&/g' | xargs -I{} myCmd {} arg1 arg2

या प्रत्येक पंक्ति बोली:

tail myFile.txt | sed 's/"/"\\""/g;s/.*/"&"/' | xargs -I{} myCmd {} arg1 arg2

यदि आप चाहते हैं कि 10 अंतिम एनयूएल-सीमांकित रिकॉर्ड myFile.txt(लेकिन फिर वह पाठ फ़ाइल नहीं होगी), तो आपको कॉल \nकरने \0से पहले कन्वर्ट tailकरना होगा जिसका अर्थ है कि फ़ाइल को पूरी तरह से पढ़ना होगा:

tr '\n\0' '\0\n' < myFile.txt |
  tail |
  tr '\n\0' '\0\n' |
  xargs -r0i myCmd {} arg1 arg2

संपादित करें (जब से आपने अपने प्रश्न में परिवर्तन किया tailहै tail -f):

पिछले एक से ऊपर स्पष्ट रूप से समझ में नहीं आता है tail -f

xargs -d '\n'एक काम करेंगे, लेकिन अन्य लोगों के लिए, आप एक बफरिंग समस्या होगा। में:

tail -f myFile.txt | tr '\n' '\0' | xargs -r0i myCmd {} arg1 arg2

trजब इसका टर्मिनल (यहां, एक पाइप) पर नहीं जाता है तो इसका आउटपुट बफ़र करता है। IE, यह तब तक कुछ भी नहीं लिखेगा जब तक कि इसे लिखने के लिए डेटा का एक बफर पूर्ण (8kiB जैसा कुछ) जमा न हो। जिसका अर्थ myCmdबैचों में कहा जाएगा।

GNU या FreeBSD सिस्टम पर, आप कमांड के trसाथ बफरिंग व्यवहार को बदल सकते हैं stdbuf:

tail -f myFile.txt | stdbuf -o0 tr '\n' '\0' |
  xargs -r0i myCmd {} arg1 arg2

मैं वास्तव में पूंछ पर -f विकल्प का उपयोग करने के लिए था, जो लगातार लाइनों को प्रिंट करता है क्योंकि वे अंदर आते हैं। मुझे नहीं लगता था कि यह कोई फर्क नहीं पड़ेगा, लेकिन जाहिर है वह ऐसा करता है। -F विकल्प के साथ आपका समाधान काम नहीं करता है।
लार्स

tail -f myFile.txt | xargs -r0i -d '\n' myCmd "{}" "||" "||"काम करने के लिए लगता है! धन्यवाद।
लार्स

@ लार्स, सॉरी, -iविकल्प एक वैकल्पिक तर्क लेता है, इसलिए -i0काम नहीं करेगा। उन्हें tail -fअंतिम एक को छोड़कर सभी के साथ काम करना चाहिए , लेकिन सावधान रहें कि बफरिंग के कारण, xargsइसके इनपुट मिलने से पहले देरी होगी tr। आप stdbuf -o0 tr '\n' '\0'इसके बजाय भाग कर बदल सकते हैं tr '\n' '\0'
स्टीफन चेज़लस
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.