我在Strawberry perl中运行一个脚本,它读取文件并进行一些处理并将输出写入另一个文件。我有时会在原始文件中遇到一些非ASCII字符(扩展名)时收到此消息。
Wide character in print at cv2pf.pl line 348, <$fh> chunk 1307
含义是什么,我该如何解决?它似乎对输出文件没有任何影响,除非我遗漏了什么。
这里给出的解决方案: Decode unicode escape characters with perl无法解决问题。我正在将输出写入文件而不是控制台,因此解决方案不起作用。
我在打开文件时指定了UTF-8,但它仍然给出了错误
# Detect the file type UTF-8 or not
if (!open(READ,$sourcefile))
{
print "Error: Could not open $sourcefile for detecting.\n";
next;
}
my $line = <READ>;
my $enc = Encode::Detect::Detector::detect($line);
print "File encoding: $enc\n";
close READ;
if ($enc eq "UTF-8")
{
if (!open(READ,'<:encoding(UTF-8)',$sourcefile))
{
print "Error: Could not open UTF-8 $sourcefile for reading.\n";
next;
}
}
else
{
if (!open(READ,$sourcefile))
{
print "Error: Could not open $sourcefile for reading.\n";
next;
}
}
if (!open($fh,"+>:encoding(utf8)","$base.m.csv"))
{
print "Error: Could not open $base.m.csv for reading/writing.\n";
next;
}
undef $/;
$_=<READ>;
# remove the BOM
if ($enc eq "UTF-8")
{
$_ =~ s/\x{FEFF}//g;
}
# convert unix line ending to dos
$_ =~ s/\r?\n|\r/\r\n/g;
print $fh $_;
close READ;
$/ = "\r\n";
seek ($fh,0,0);
my $csv = Text::CSV->new ( { allow_whitespace => 1, binary => 1 } ); # should set binary attribute.
在输出中,我看到源文件是UTF-8,相应地被打开为UTF-8文件。
文件编码:UTF-8
我在这里缺少什么?
要求的其他代码:
第348行
print {$handles{$currency}} "P" . $row->{'Name'} . "\r\n";
my %handles;
curcheck: while ( $row = $csv->getline_hr( $fh ) ) {
my $currency=$row->{'Currency'};
if (exists $handles{$currency}) {
next curcheck;
}
$handles{$currency}=return_fh();
if (!open($handles{$currency},">:encoding(utf8)","$base-$currency.out"))
{
print "Error: Could not open $base-$currency.out for writing.\n";
next file;
}
binmode($handles{$currency})
}
seek ($fh,0,0);
$row = $csv->getline ($fh);
...
sub return_fh {
local *FH;
return *FH;
}
答案 0 :(得分:1)
经过大量挖掘后发现错误是因为您使用显式模式:encoding(utf8)
显式打开文件句柄的哈希,然后立即将其更改为未编码 binmode
以下对于任何Perl程序都非常重要
使用use strict
和use warnings 'all'
声明所有变量尽可能接近其第一个使用点;通常在定义时
使用词汇文件句柄而不是全局句柄。例如
unless ( open my $read, '<:encoding(UTF-8)', $sourcefile ) {
print "Error: Could not open UTF-8 $sourcefile for reading.\n";
next;
}
它们作为子程序参数传递要简单得多。并且Perl将在超出范围时自动关闭
使用$var = undef
代替undef $var
将变量设置为undef
。并使用local $/
暂时对全局变量执行此操作,并使用代码块{ ... }
来限制更改的范围
答案 1 :(得分:-1)
解决方案是# Add encoding layer to STD*
use Win32 qw( );
use open ':std', ':encoding(cp'.Win32::GetConsoleOutputCP().')';
# Set default encoding layer for files open in scope of this.
use open ':encoding(UTF-8)';
open(my $fh, '>', $qfn)
or die("Can't create \"$qfn\": $!\n");
,具有适当的编码层。您正在写入文件而不是STDOUT的事实不会改变任何内容。
urlConnection.setRequestMethod("POST");