1

我正在用 Perl 编写以表格格式指导我的报告,但是每当数据填充的文本太长时我就会遇到问题。有没有办法编写代码,以便它可以将行包装成多个。这是我的代码和输出。谢谢!

printf "\n%-${max1}s %-${max2}s %-15s\n", "====", "====", "=====" ;
printf "%-${max1}s %-${max2}s %-15s\n", "Code", "Item", "Group" ;
printf "%-${max1}s %-${max2}s %-15s\n", "====", "====", "=====" ;

foreach my $f (@{$rpt_ptr}) {
printf "%-${max1}s %-${max2}s %-15s\n", "$$f{code}", "$$f{item}", "$$f{group}", 
}

如果我的项目列表太长,输出表将被扩展太长,即:-

====  =====                                                                                =====      

Code  Item                                                                                 Group

====  =====                                                                                =====

A1011 aaaaaa, bbbbb, ccccc, ddddd, eeeee, fffff, ggggg, hhhhh, iiiii, jjjjjj, kkkkk, llll    B
    B101  cccccc                                                                                 A

如果我能拿出一张这样的桌子,我会很高兴:

====  =====                                                                                =====      
Code  Item                                                                                 Group
====  =====                                                                                =====
A1011 aaaaaa, bbbbb, ccccc, ddddd,                                                           B
      eeeee, fffff, ggggg, hhhhh,   
      iiiii, jjjjjj, kkkkk, llll
B101  cccccc                                                                                 A

我将如何实现这一目标?

4

5 回答 5

3

Perl 最初是为格式化文本文件而编写的。它包括一个相当有趣的表单生成工具,包括以您指定的方式换行的能力。我已经很久很久没有看到它使用了,但它仍然是语言的一部分。

它在 perldoc 下perlform


例子

#! /usr/bin/env perl

use strict;
use warnings;
use feature qw(say);

my ($invoice, $description, $amount);
while ( chomp ( my $line = <DATA> ) ) {
    ( $invoice, $description, $amount ) = split /:/ => $line;
    write;
}

format STDOUT_TOP =
Invoice   Description       Amount
=======   ===========       =======
.
format STDOUT = 
@<<<<<<   ^<<<<<<<<<<<<<<   @###.##
$invoice, $description,     $amount
          ^<<<<<<<<<<<<<<
          $description
          ^<<<<<<<<<<<<<<
          $description
          ^<<<<<<<<<<<<<<
          $description
          ^<<<<<<<<<<<<<<
          $description
.
__DATA__
One:This line contans a lot of text that I have to process and I have no idea what it is:2.30
Two:Here's another line that contains lots of data that won't fit on a single line:4.40
Three:And one more line of extra long data that may or may not fit on a single line:5.10

输出

Invoice   Description       Amount
=======   ===========       =======
One       This line            2.30
          contans a lot
          of text that I
          have to process
          and I have no
Two       Here's another       4.40
          line that
          contains lots
          of data that
          won't fit on a
Three     And one more         5.10
          line of extra
          long data that
          may or may not
          fit on a single
于 2013-01-17T03:16:42.037 回答
1

formats真的是要走的路。

这是使用Perl6::Form的解决方案:

use Perl6::Form;

my @data = (
    ['A1011', 'aaaaaa, bbbbb, ccccc, ddddd, eeeee, fffff, ggggg, hhhhh, iiiii, jjjjjj, kkkkk, llll', 'B'],
    ['B101', 'cccccc', ''],
);

print form
    "====  =====                                              =====",
    "Code  Item                                               Group",
    "====  =====                                              =====";

foreach (@data) {
    print form
        "{<<<<}{[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[}             {<<}", @$_ ;
}
于 2013-01-17T07:58:42.657 回答
0

如果您想要一些非常基本/特定(不可靠)的东西,请每隔四个逗号强制换行:

在你的循环之前printf

$$f{item} =~ s/(,[^,]+,[^,]+,[^,]+,)/$1\n/g;

正如大卫建议的那样,最好的选择可能是使用perlform (5.8.8 适合你)

于 2013-01-21T03:19:25.453 回答
0

我终于通过以下代码完成了它,在这里发布以分享:-

foreach my $f (@{$rpt_ptr}) {
#   printf "%-${max1}s %-${max2}s %-15s\n", "$$f{code}", "$$f{item}", "$$f{group}", 
format STDOUT_TOP =
===============     =========================     ========= 
Code                 Item                     Group
===============     =========================     ========= 
.

format STDOUT =
@<<<<<<<<<<<<<<     ^<<<<<<<<<<<<<<<<<<<<<<<<<     @<<<<<<<<
$$f{code}               $$f{item}                                              $$f{group} 
~~                ^<<<<<<<<<<<<<<<<<<<<<<<<
                   $$f{item}
.
write ;
}

对于所有回答我问题的人,非常感谢您的帮助,我非常感谢!

于 2013-01-22T07:00:51.830 回答
0

您可以使用正则表达式来包装文本。由于您正在逐行打印文件,因此您可以在标量变量中获取每一行并检查该标量变量的长度并插入换行符\n

喜欢:

    $var = "\n%-${max1}s %-${max2}s %-15s\n", "====", "====", "=====" ;
    $var .= "%-${max1}s %-${max2}s %-15s\n", "Code", "Item", "Group" ;
    $var .= "%-${max1}s %-${max2}s %-15s\n", "====", "====", "=====" ;

    ## Adding new line character after 20 characters.
    my $startIndex = 0;

    while( ($startIndex < length($var) && (length($var) > 20) ) {
     print substr($var, $startIndex, 20)  . "\n";
     $startIndex = $startIndex + 20;
    }
于 2013-01-17T05:44:06.247 回答