लाइनों के ब्लॉक छँटाई


12

मेरे पास एक फाइल है जिसमें 4n लाइनें हैं। यहाँ इसका एक अंश है जिसमें 8 रेखाएँ हैं

6115 8.88443
6116 6.61875
6118 16.5949
6117 19.4129
6116 6.619 
6117 16.5979 
6118 19.4111
6115 8.88433  

मैं जो करना चाहता हूं वह एक ब्लॉक को सॉर्ट करना है, जहां प्रत्येक ब्लॉक में पहले कॉलम के आधार पर 4 लाइनें होती हैं। अंश के लिए आउटपुट नीचे दिखाए गए अनुसार दिखना चाहिए।

6115 8.88443
6116 6.61875
6117 19.4129
6118 16.5949
6115 8.88433 
6116 6.619 
6117 16.5979 
6118 19.4111 

जवाबों:


16

एक विकल्प यह है कि आप प्रत्येक N लाइनों (अपने मामले में N = 4) में प्रारंभिक सीरियल नंबर उपसर्ग जोड़ने के लिए का उपयोग करें । फिर उपसर्ग को प्राथमिक सॉर्टिंग कॉलम के रूप में फ़ीड करें sort

N = 4 के साथ उदाहरण:

awk '{print int((NR-1)/4), $0}' file.txt | sort -n -k1,1 -k2,2 | cut -f2- -d' '

7

यदि यह एक बंद है और आप अजगर, पर्ल या जाग सीखना नहीं चाहते हैं, तो आप मूल splitऔर sortआज्ञाओं के साथ जा सकते हैं ।

पहले -l विकल्प के साथ फाइल को 4 लाइन के टुकड़ों में विभाजित करें :

split -a 6 -l 4 input_file my_prefix_
for fn in my_prefix_*; do
    sort -n -o $fn $fn
done
cat my_prefix_* > output_file
rm my_prefix_*

sort -nपहले कॉलम (999 1234 से पहले) के संख्यात्मक मान द्वारा प्रकार। -a 626 ^ 6 * 4 लाइनों वाली फ़ाइल का ध्यान रखना चाहिए। my_prefix_आपके द्वारा काम करने वाली निर्देशिका के लिए कुछ अनूठा होना चाहिए।


3

आप इसे पर्ल के साथ कर सकते हैं:

perl -nle '
   push @a,$_;
   unless($. % 4){
       print join "\n",sort {$a <=> $b} @a; # Sort @a, and print its contents
       @a = (); # Empty @a to start a new block
   }
' your_file

यह कैसे काम करता है

  • -n-> प्रत्येक इनपुट लाइन के लिए कोड चलाएं (और वर्तमान लाइन को अंदर डालें $_)
  • -l -> किसी भी आउटपुट के लिए एक नई लाइन संलग्न print
  • -e -> निम्नलिखित स्ट्रिंग को पर्ल कोड के रूप में निष्पादित करें
  • प्रत्येक पंक्ति को सरणी में जोड़ा जाता है @a
  • $.वर्तमान लाइन नंबर को धारण करता है और जब तक कि संख्या शून्य मॉडुलो 4 के अनुरूप नहीं होती है, तब तक हम काम करते रहते हैं। यदि यह है शून्य सापेक्ष 4 अनुकूल है, हम एक लाइन जिनकी संख्या 4 (एक ब्लॉक के अंत में) की एक बहु है, ऐसी स्थिति में, हम प्रकार में प्रविष्टियों पर पहुँच गए हैं @aसंख्यात्मक आरोही क्रम में और प्रविष्टियों क्रमबद्ध सरणी में प्रिंट मानक आउटपुट के लिए एक नई पंक्ति से जुड़ गया।

2

बॉर्न जैसी शेल का उपयोग करना,

while read a ; do                                           # Try reading a line.
    read b ; read c ; read d                                # OK, read 3 more.
    printf '%s\n%s\n%s\n%s\n' "$a" "$b" "$c" "$d" | sort -n # Sort them.
done < data

2

यहाँ कुछ "शुद्ध" awkसमाधान हैं:

यदि अनुक्रमणिका हमेशा समान वृद्धिशील पूर्णांक अनुक्रम (6115-6119) है, जैसा कि आपके नमूना-डेटा में है, तो आप एक एल्गोरिथम "शॉर्टकट" का उपयोग कर सकते हैं:

awk '{a[$1]=$0} !(NR%4){for(i=6115;i<6119;print a[i++]);}'

यह करता है

  • सरणी में सभी पंक्तियों को जोड़ें a, सूचकांक पदों पर वितरित 6115-6119
  • !(NR%4)वांछित क्रम में मुद्रित करने के लिए सरणी सामग्री के माध्यम से प्रत्येक 4 वीं पंक्ति ( ) पर लूप।

यदि आपके संख्यात्मक सूचकांक हमेशा चार समान होते हैं, लेकिन पूर्णांक अनुक्रम नहीं बढ़ रहा है, तो आपको क्रमबद्ध करना होगा:

awk '{a[$1]=$0} !(NR%4){asort(a,b); for(i=1;i<5;print b[i++]);}'

नोट: यह GNU awk के साथ है, अन्य समर्थन नहीं कर सकते हैं asort


यदि हर ब्लॉक के चार अलग-अलग संख्यात्मक आईडी हो सकते हैं:

awk '{a[$1]=$0} !(NR%4){asort(a); for(i=1;i<5;print a[i++]); delete a}'

नोट: @ गिल्स से सेल्फ-आंसर (+2) का यह उपयोग deletePOSIX का (अभी तक) नहीं है, लेकिन सार्वभौमिक रूप से समर्थित है


सही ™ उपयोग के साथ एक संस्करण delete:

awk '{a[$1]=$0} !(NR%4){asort(a); for(i=1;i<5;delete a[i++]){print a[i]}}'

अधिक मेमोरी और आयामों का उपयोग किए बिना, बिना डिलीट किए एक संस्करण:

awk '{a[n][$1]=$0} !(NR%4){asort(a[n]); for(i=1;i<5;print a[n][i++]); n++}

1

आप आर के साथ एक स्वच्छ समाधान प्राप्त कर सकते हैं। यदि उपरोक्त तालिका "table.txt" नामक फ़ाइल में है, तो निम्न चरणों का पालन करें। वांछित परिणाम "tableout.txt" फ़ाइल में होगा।

> x = read.table("table.txt", col.names=c("a", "b"))
> x
     a        b
1 6115  8.88443
2 6116  6.61875
3 6118 16.59490
4 6117 19.41290
5 6116  6.61900
6 6117 16.59790
7 6118 19.41110
8 6115  8.88433
> x["index"] = c(rep(1, 4), rep(2, 4))
> x
     a        b index
1 6115  8.88443     1
2 6116  6.61875     1
3 6118 16.59490     1
4 6117 19.41290     1
5 6116  6.61900     2
6 6117 16.59790     2
7 6118 19.41110     2
8 6115  8.88433     2     
> xord = x[with(x, order(index, a)), ]
> xord
     a        b index
1 6115  8.88443     1
2 6116  6.61875     1
4 6117 19.41290     1
3 6118 16.59490     1
8 6115  8.88433     2
5 6116  6.61900     2
6 6117 16.59790     2
7 6118 19.41110     2
> write.table(xord[,1:2], "tableout.txt", row.names=FALSE, col.names=FALSE)

यह भी देखें कि आर में कॉलम (एस) द्वारा डेटाफ्रेम कैसे सॉर्ट करें

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