【问题标题】:Are single element lists allowed in perl?perl 中是否允许使用单个元素列表?
【发布时间】:2017-06-09 20:53:40
【问题描述】:

我正在尝试从 AJAX 请求(使用 Catalyst)动态创建值列表,如下所示:

my @listofvalues         = @{$params->{parameter_with_many_values}};

然后我遍历列表以进行数据库插入(每个值一个)。由于我需要遍历上面的各种列表,因此我需要访问列表的索引。我目前正在这样做:

foreach my $key (0 .. $#listofvalues){
  $table_model->new({
    field1                => $listofvalues[$key],
    field2                => $x,
    field3                => $another_listofvalues[$key]
    field4                => $yet_another_listofvalues[$key]
  });
} 

当请求中收到两个或更多元素时,这似乎可以正常工作。每当收到单个元素时,我都会收到类似的错误

[error] Caught exception in pbitdb::Controller::Subjects->add "Can't use string ("1") as an ARRAY ref while "strict refs" in use at /home/lioneluranl/svn/pbitdb/pbitdb/script/../lib/pbitdb/Controller/Subjects.pm line 119."

在这种情况下,1 是收到的值,第 119 行 是声明 @listofvalues 的行。

现在我已经尝试了几种方法来解决这个问题,但还没有发现任何可以双向工作的方法(对于单个值或各种值)。有什么建议吗?

【问题讨论】:

  • 问题在于设置$params->{parameter_with_many_values}的任何代码。它以文字字符串“1”结束。
  • field4前少了一个逗号。
  • 这意味着 $params->{parameter_with_many_values} 不包含对数组的引用。它包含标量值“1”。

标签: ajax list perl catalyst


【解决方案1】:

是的,单元素列表在 Perl 中是可以的,数组和对此类数组的引用也是如此。

#!/usr/bin/perl
use warnings;
use strict;

use Data::Dumper;

sub new {
    print Dumper \@_;
}

my $table_model = 'main';

for my $values ( [ 'a' .. 'c' ],
                 [ 'd' ]
) {
    my $params = { parameter_with_many_values => $values };
    my @listofvalues = @{ $params->{parameter_with_many_values} };
    my @another_listofvalues = map uc, @listofvalues;

    for my $key (0 .. $#listofvalues) {
        my $x = rand;
        $table_model->new({
            field1 => $listofvalues[$key],
            field2 => $x,
            field3 => $another_listofvalues[$key]
        });
    }
}

你如何填充$params->{parameter_with_many_values}

更新

似乎Catalyst::Request 应该提到他们的“安全”参数应该如下处理:

#!/usr/bin/perl
use warnings;
use strict;

use Data::Dumper;

for my $params ( { param_with_many_values => 'a' },
                 { param_with_many_values => [ 'a' .. 'e' ] },
                 { something => 'else' }
) {
    my $value_or_values = $params->{param_with_many_values};
    my @list_of_values = ref $value_or_values     ? @$value_or_values
                       : defined $value_or_values ? $value_or_values
                                                  : ();
    print Dumper \@list_of_values;
}

【讨论】:

  • Population 来自 Catalyst::Request perl 模块,不幸的是它就是这样工作的(这意味着给定的参数可以是标量或数组,具体取决于有多少输入在表单中带有相同的名称)。没有尝试映射,但似乎是一个很好的解决方法。让我测试...
  • 哦,看来您需要my $value_or_values = $params->{param_with_many_values}; my @list_of_values = ref $value_or_values ? @$value_or_values : $value_or_values;,并且您需要检查该值是否存在以防止undef 潜入数组。
  • 我刚刚这样做了,正要发布答案。这就像一个魅力。非常感谢您的帮助:)
【解决方案2】:

首先,您要问的是数组(一种变量),而不是列表(一个可以有多种定义的模糊术语,这里没有一个是相关的)。

是的,你可以拥有一个只有一个元素的数组。

$ perl -e'my @a = "ele"; CORE::say 0+@a; CORE::say for @a;'
1
ele

这不是问题。问题是

@{$params->{parameter_with_many_values}}

预计

$params->{parameter_with_many_values}

包含对数组的引用,但它包含1。它可能是使用设置的

$params->{parameter_with_many_values} = @a;   # Assigns number of elements

而不是

$params->{parameter_with_many_values} = \@a;

【讨论】:

  • 以上都是。不幸的是,我无法更改处理请求的模块,但是一旦我得到它,我会发布解决方法。感谢您的输入:)
猜你喜欢
  • 2023-03-18
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-01-12
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-08-18
相关资源
最近更新 更多