如何添加两列 DataFrame 并使用前缀名称重命名 bash
How to Add Two Columns of DataFrame and Rename it with Prefix Name using bash
The original Data looks like
ID,kgp11274425_A,kgp11274425_HET,kgp5732633_C,kgp5732633_HET,rs707_G,rs707_HET,kgp75_T,kgp75_HET
1,C,T,G,T,C,A,0,0
2,C,C,T,G,A,A,G,T
3,A,A,G,G,C,G,A,A
4,G,G,C,C,A,A,T,A
Desired Output:
ID,kgp11274425,kgp5732633,rs707,kgp75
1,CT,GT,CA,00
2,CC,TG,AA,GT
3,AA,GG,CG,AA
4,GG,CC,AA,TA
I was able to accomplish this using the following Python Script
sep = '_'
unique_cols = pd.Index(map(lambda x : x.split(sep, 1)[0], df.columns)).unique()
results = []
columns = []
for col in unique_cols:
my_cols = [x for x in df.columns if x.startswith(col)]
results.append(df[my_cols].sum(axis=1).values)
columns.append(col)
new_df = pd.DataFrame(results).T
new_df.columns = columns
但是这次我得到了 522rows & 5311137cols (5GB) 数据,Python 无法读取文件。所以我需要使用 bash 命令 运行 相同的 python 逻辑,bash 的新手请帮助
输入:
$ cat raw.dat
ID,kgp11274425_A,kgp11274425_HET,kgp5732633_C,kgp5732633_HET,rs707_G,rs707_HET,kgp75_T,kgp75_HET
1,C,T,G,T,C,A,0,0
2,C,C,T,G,A,A,G,T
3,A,A,G,G,C,G,A,A
4,G,G,C,C,A,A,T,A
一个awk
想法:
awk -F, '
{ printf # print 1st column
for (i=2;i<=NF;i=i+2) { # process columns 2 at a time
if (FNR==1) # 1st row? then ...
printf "%s%s", FS, substr($i,1,index($i,"_")-1) # print ith column sans the '_xxxx' suffix
else
printf "%s%s%s", FS, $i, $(i+1) # print the (i)th and (i+1)th columns
}
print ""
}
' raw.dat
这会生成:
ID,kgp11274425,kgp5732633,rs707,kgp75
1,CT,GT,CA,00
2,CC,TG,AA,GT
3,AA,GG,CG,AA
4,GG,CC,AA,TA
注意: OP 的所需输出似乎不是 single-space 分隔的,也不是制表符分隔的,所以我选择了一个 space; OP 可以修改 printf
格式字符串以完成所需的格式
基本方法是模拟 FPAT 的功能,但以更便携的方式 - 此代码已经过测试并确认可以在 gawk 5.1.1
上运行,包括标志 -ce/-Pe
、mawk 1.3.4
、mawk 1.9.9.6
和macOS 12.3 nawk
。
ID, kgp11274425 kgp5732633 rs707 kgp75
1 CT GT CA 00
2 CC TG AA GT
3 AA GG CG AA
4 GG CC AA TA
[mng]awk 'BEGIN {
FS = "[_][^_]+[_][^,]+[,]?[ " (substr(\
OFS = "\t\t", _+=_=_~_)) "]*"
print $( (getline) < -(NF=NF) )
__ = (__="[^ \t]+") substr(_=substr(___="&",_) \
"[ \t]+", index(_, "[") ) __ "|_"
FS = "^$"
} gsub(__,___) + gsub(_,"")' datafile.txt
通过使用 regex
,它避免了手动循环
字段,即使一次 2 个字段。 </code> (<code>ACK + ETX
) 只是
ASCII-only SEP
比 SUBSEP
(4
) 或
null-byte ([=23=]
).
第二个优点是通过独立的逻辑
试图模拟 FPAT
,FS
可以直接设置为 ^$
,
因为拆分各个领域的理由是不
不再适用...
。 . .希望这可以帮助推动事情发展,因为 OP 确实提到了 500K+
列。
- 此解决方案的注意事项是它不会尝试以完美的方式排列所有内容,而是使用
\t\t
2 个水平制表符作为粗略的解决方案。
综合 5GB
文件基准测试: 1 min 14 secs
用于 5.12GB
文件,read-in 吞吐率为 70.5 MB/s
out9: 2.54GiB 0:01:14 [34.9MiB/s] [34.9MiB/s]
[====================================>] 102%
in0: 5.12GiB 0:01:14 [70.5MiB/s] [70.5MiB/s]
[====================================>] 100%
( pvE 0.1 in0 < testcase_dna_002.txt | gawk -be ; )
73.44s user 2.20s system 101% cpu 1:14.37 total
nice pv -pteba -i 0.25 -r --size='2540m' -cN out9 > /dev/null 0.24s
user 0.73s system 1% cpu 1:14.37 total
The original Data looks like
ID,kgp11274425_A,kgp11274425_HET,kgp5732633_C,kgp5732633_HET,rs707_G,rs707_HET,kgp75_T,kgp75_HET
1,C,T,G,T,C,A,0,0
2,C,C,T,G,A,A,G,T
3,A,A,G,G,C,G,A,A
4,G,G,C,C,A,A,T,A
Desired Output:
ID,kgp11274425,kgp5732633,rs707,kgp75
1,CT,GT,CA,00
2,CC,TG,AA,GT
3,AA,GG,CG,AA
4,GG,CC,AA,TA
I was able to accomplish this using the following Python Script
sep = '_'
unique_cols = pd.Index(map(lambda x : x.split(sep, 1)[0], df.columns)).unique()
results = []
columns = []
for col in unique_cols:
my_cols = [x for x in df.columns if x.startswith(col)]
results.append(df[my_cols].sum(axis=1).values)
columns.append(col)
new_df = pd.DataFrame(results).T
new_df.columns = columns
但是这次我得到了 522rows & 5311137cols (5GB) 数据,Python 无法读取文件。所以我需要使用 bash 命令 运行 相同的 python 逻辑,bash 的新手请帮助
输入:
$ cat raw.dat
ID,kgp11274425_A,kgp11274425_HET,kgp5732633_C,kgp5732633_HET,rs707_G,rs707_HET,kgp75_T,kgp75_HET
1,C,T,G,T,C,A,0,0
2,C,C,T,G,A,A,G,T
3,A,A,G,G,C,G,A,A
4,G,G,C,C,A,A,T,A
一个awk
想法:
awk -F, '
{ printf # print 1st column
for (i=2;i<=NF;i=i+2) { # process columns 2 at a time
if (FNR==1) # 1st row? then ...
printf "%s%s", FS, substr($i,1,index($i,"_")-1) # print ith column sans the '_xxxx' suffix
else
printf "%s%s%s", FS, $i, $(i+1) # print the (i)th and (i+1)th columns
}
print ""
}
' raw.dat
这会生成:
ID,kgp11274425,kgp5732633,rs707,kgp75
1,CT,GT,CA,00
2,CC,TG,AA,GT
3,AA,GG,CG,AA
4,GG,CC,AA,TA
注意: OP 的所需输出似乎不是 single-space 分隔的,也不是制表符分隔的,所以我选择了一个 space; OP 可以修改 printf
格式字符串以完成所需的格式
基本方法是模拟 FPAT 的功能,但以更便携的方式 - 此代码已经过测试并确认可以在 gawk 5.1.1
上运行,包括标志 -ce/-Pe
、mawk 1.3.4
、mawk 1.9.9.6
和macOS 12.3 nawk
。
ID, kgp11274425 kgp5732633 rs707 kgp75
1 CT GT CA 00
2 CC TG AA GT
3 AA GG CG AA
4 GG CC AA TA
[mng]awk 'BEGIN {
FS = "[_][^_]+[_][^,]+[,]?[ " (substr(\
OFS = "\t\t", _+=_=_~_)) "]*"
print $( (getline) < -(NF=NF) )
__ = (__="[^ \t]+") substr(_=substr(___="&",_) \
"[ \t]+", index(_, "[") ) __ "|_"
FS = "^$"
} gsub(__,___) + gsub(_,"")' datafile.txt
通过使用
regex
,它避免了手动循环 字段,即使一次 2 个字段。</code> (<code>ACK + ETX
) 只是ASCII-only SEP
比SUBSEP
(4
) 或 null-byte ([=23=]
).第二个优点是通过独立的逻辑 试图模拟
FPAT
,FS
可以直接设置为^$
, 因为拆分各个领域的理由是不 不再适用...。 . .希望这可以帮助推动事情发展,因为 OP 确实提到了
500K+
列。
- 此解决方案的注意事项是它不会尝试以完美的方式排列所有内容,而是使用
\t\t
2 个水平制表符作为粗略的解决方案。
综合 5GB
文件基准测试: 1 min 14 secs
用于 5.12GB
文件,read-in 吞吐率为 70.5 MB/s
out9: 2.54GiB 0:01:14 [34.9MiB/s] [34.9MiB/s]
[====================================>] 102%
in0: 5.12GiB 0:01:14 [70.5MiB/s] [70.5MiB/s]
[====================================>] 100%
( pvE 0.1 in0 < testcase_dna_002.txt | gawk -be ; )
73.44s user 2.20s system 101% cpu 1:14.37 total
nice pv -pteba -i 0.25 -r --size='2540m' -cN out9 > /dev/null 0.24s
user 0.73s system 1% cpu 1:14.37 total