第一行数字排序

时间:2016-08-19 20:10:19

标签: bash macos sorting carriage-return numerical

我有一个excel中有近900行的文件,我已将其保存为制表符分隔的.txt文件。我想按照第一列中给出的数字对文本文件进行排序(它们的范围在0到2250之间)。其他列都是不同长度的数字和字母,例如

myfile.txt的:

0251  abcd 1234,24 bcde
2240  efgh 2345,98 ikgpppm
0001  lkjsi 879,09 ikol

我已经尝试了

sort -k1 -n myfile.txt > myfile_num.txt

但我只是得到一个新名称相同的文件。我想得到:

myfile_num.txt

0001  lkjsi 879,09 ikol 
0251  abcd 1234,24 bcde
2240  efgh 2345,98 ikgpppm

我做错了什么?我猜它很简单,但我很感激我能得到的任何帮助!我只知道一个小的bash脚本,所以如果脚本是一个非常简单的单行程,我可以理解它是好的:)

谢谢:)

3 个答案:

答案 0 :(得分:1)

使用此选项将旧版Mac OS回车转换为换行符:

tr '\r' '\n' < myfile.txt | sort

答案 1 :(得分:0)

如上所述here你可能会遇到这个问题(在你提出的其他伪跟进重复question中,是的,你做过了)

tr '\r' '\n' < myfile.txt | sort -n

在MSYS上可以正常工作,但在某些平台上你可能需要添加:

export LC_CTYPE=C

tr会将该文件视为文本文件,并可能在达到最大行限制后将其标记为已损坏。

显然我无法测试它,但我相信它会解决问题,因为我在链接的答案中读了解。

答案 2 :(得分:0)

python方法(python 2&amp; 3兼容),免受所有shell问题的影响。效果很好,便携。我注意到输入文件有一些&#39; 0x8C&#39; chars(奇异点),可能令人困惑的tr命令。 这在下面妥善处理:

import csv,sys

# read the file as binary, as it is not really text
with open("Proteins.txt","rb") as f:
    data = bytearray(f.read())
    # replace 0x8c char by classical dots
    for i,c in enumerate(data):
        if c>0x7F: # non-ascii: replace by dot
            data[i] = ord(".")

    # convert to list of ASCII strings (split using the old MAC separator)
    lines = "".join(map(chr,data)).split("\r")

    # treat our lines as input for CSV reader
    cr = csv.reader(lines,delimiter='\t',quotechar='"')

    # read all the lines in a list    
    rows = list(cr)
    # perform the sort (tricky)
    # on first row, numerical, removing the leading 0 which is illegal
    # in python 3, and if not numerical, put it at the top

    rows = sorted(rows,key=lambda x : x[0].isdigit() and int(x[0].strip("0")))

# write back the file as a nice, legal, ASCII tsv file

if sys.version_info < (3,):
    f = open("Proteins_sorted_2.txt","wb")
else:
    f = open("Proteins_sorted_2.txt","w",newline='')

cw = csv.writer(f,delimiter='\t',quotechar='"')
cw.writerows(rows)
f.close()