Regex 使用awk/perl检查小数点,如果没有小数点,则将其添加到末尾
我有test.dat文件,其值如下所示:Regex 使用awk/perl检查小数点,如果没有小数点,则将其添加到末尾,regex,perl,shell,awk,Regex,Perl,Shell,Awk,我有test.dat文件,其值如下所示: 20150202,abc,,,,3625.300000,,,,,-5,,,,,,,,,,,,,,,,,,,,,, 20150202,def,,,,32.585,,,,,0,,,,,,,,,,,,,,,,,,,,,, 20150202,xyz,,,,12,,,,,0.004167,,,,,,,,,,,,,,,,,,,,,, Use of uninitialized value in split at test.pl line 11
20150202,abc,,,,3625.300000,,,,,-5,,,,,,,,,,,,,,,,,,,,,,
20150202,def,,,,32.585,,,,,0,,,,,,,,,,,,,,,,,,,,,,
20150202,xyz,,,,12,,,,,0.004167,,,,,,,,,,,,,,,,,,,,,,
Use of uninitialized value in split at test.pl line 11, <$fh> line 1.
Use of uninitialized value in pattern match (m//) at test.pl line 13, <$fh> line 1.
Use of uninitialized value in pattern match (m//) at test.pl line 13, <$fh> line 1.
Use of uninitialized value in join or string at test.pl line 15, <$fh> line 1.
....
我的预期输出如下所示:
20150202,abc,,,,3625.300000,,,,,-5.,,,,,,,,,,,,,,,,,,,,,,
^. added here
20150202,def,,,,32.585,,,,,0.,,,,,,,,,,,,,,,,,,,,,,
^. added here
20150202,xyz,,,,12.,,,,,0.004167,,,,,,,,,,,,,,,,,,,,,,
^. added here
因此,如果第6列和第11列中没有小数点,那么我们应该在文件末尾添加“.”
我尝试了下面的代码,但在拆分过程中抛出了错误消息
#!/usr/bin/perl
use strict;
use warnings;
my $filename = 'test.dat';
open my $fh, $filename or die "Could not open file '$filename': $!";
my @cols_to_change = qw ( 6 11 );
while (my $val = <$fh>) {
my @row = split (/,/);
foreach my $col ( @cols_to_change ) {
unless ( $row[$col] =~ m/\./ ) { $row[$col] .= '.' }
}
print join ( ',', @row );
}
#/usr/bin/perl
严格使用;
使用警告;
my$filename='test.dat';
打开我的$fh、$filename或死亡“无法打开文件“$filename”:$!”;
my@cols_to_change=qw(6 11);
while(my$val=){
我的@row=拆分(/,/);
foreach my$col(@cols\u to\u change){
除非($row[$col]=~m/\./){$row[$col].='.}
}
打印联接(“,”,@行);
}
我收到的错误信息如下:
20150202,abc,,,,3625.300000,,,,,-5,,,,,,,,,,,,,,,,,,,,,,
20150202,def,,,,32.585,,,,,0,,,,,,,,,,,,,,,,,,,,,,
20150202,xyz,,,,12,,,,,0.004167,,,,,,,,,,,,,,,,,,,,,,
Use of uninitialized value in split at test.pl line 11, <$fh> line 1.
Use of uninitialized value in pattern match (m//) at test.pl line 13, <$fh> line 1.
Use of uninitialized value in pattern match (m//) at test.pl line 13, <$fh> line 1.
Use of uninitialized value in join or string at test.pl line 15, <$fh> line 1.
....
在test.pl第11行第1行的拆分中使用未初始化值。
在test.pl第13行第1行的模式匹配(m/)中使用未初始化值。
在test.pl第13行第1行的模式匹配(m/)中使用未初始化值。
在test.pl第15行第1行的联接或字符串中使用未初始化的值。
....
我不允许使用任何额外的perl模块,如Text::CSV。此外,任何使用awk的解决方案都会有很大帮助 在awk中
只是那些领域的子
awk -F, -vOFS="," '{sub(/^[^\.]+$/,"&.",$6);sub(/^[^\.]+$/,"&.",$11)}1' file
或sed
sed 's/^\(\([^,]*,\)\{5\}[^.,]\+\),/\1./;s/^\(\([^,]*,\)\{10\}[^.,]\+\),/\1./' file
这是您的错误:
while (my $val = <$fh>) {
在上面的代码中-您正在while循环中设置$val
,但是各种模式匹配和分割根本没有使用$val
还要注意-perl数组中的第一个元素是0
。因此,您可能应该保留复制的示例代码中的5和10
这:
按照要求,在输入样本数据时 为了完整性
(
IFS=,
while read -ra f; do
for i in 5 10; do
[[ ${f[i]} == *.* ]] || f[i]+=. # add a dot if not there
done
echo "${f[*]}" # quotes required here
done < file
)
20150202,abc,,,,3625.300000,,,,,-5.,,,,,,,,,,,,,,,,,,,,,,
20150202,def,,,,32.585,,,,,0.,,,,,,,,,,,,,,,,,,,,,,
20150202,xyz,,,,12.,,,,,0.004167
(
IFS=,
while read -ra f; do
for i in 5 10; do
[[ ${f[i]} == *.* ]] || f[i]+=. # add a dot if not there
done
echo "${f[*]}" # quotes required here
done < file
)
sed -r '
s/^(([^,]*,){5})([^.,]+),/\1\3.,/
s/^(([^,]*,){10})([^.,]+),/\1\3.,/
' file