【问题标题】:How to dereference hashes in Template Toolkit?如何取消引用模板工具包中的哈希?
【发布时间】:2013-09-01 15:09:40
【问题描述】:

我有以下问题:我有一个哈希引用数组,我想渲染它。

$VAR1 = \{
        'nice_key' => undef,
        'nicer_key' => '0',
        'nicest_key' => 'Miller'
      };
$VAR2 = \{
        'nice_key' => undef,
        'nicer_key' => '0',
        'nicest_key' => 'Farns'
      };
$VAR3 = \{
        'nice_key' => undef,
        'nicer_key' => '0',
        'nicest_key' => 'Woodstock'
      };
...

我将其作为\@tablerows 传递给模板。在我做的模板里面:

[% FOREACH row = tablerows %]
    <tr>
        <td>[% row %]</td>
        <td>[% row.nicer_key %]</td>
        <td>[% row.nicest_key %]</td>
    </tr>
[% END %]

[% row %] 行输出类似于REF(0x74a0160) 的内容,但其他两行只是空白。

据我了解,必须取消引用模板中的 row 变量才能调用 row.nicer_key,但使用 -&gt;{} 会导致解析器错误。

这甚至可能吗?或者我哪里做错了?

编辑: 数据结构的背景: 该程序执行以下操作:

  1. 解析包含表格的 HTML 文件
  2. 在解析时,将表的每一行读入一个散列(nice_keys 是表的单元格)并将这些散列存储到散列的散列中(我们称之为tabledata
  3. 执行一些数据库查询并将这些查询添加到内部哈希中(例如,nicest_key 不存在于原始 HTML 文件中)
  4. 以与之前相同的顺序输出 HTML 表格。

为了保持原始表的顺序,我在第 2 步中用对内部哈希的引用填充了 tablerows 数组。

Edit2: 我的意图是:

箭头表示对哈希的引用。

我如何填写这些数据

my %tabledata = ();
my @tablerows = ();
foreach (... parsing ...) {
  ...
  $tabledata{$current_no} = ();
  push @tablerows, \$tabledata{$current_no};

  $tabledata{$current_no}{$row} = $value;
}

当我转储%tabledata@tablerows 时,内容对我来说似乎是正确的。

【问题讨论】:

  • 您的问题是您的数组不包含对哈希的引用,而是对哈希引用的引用。
  • 好的.. 但这意味着,我也应该能够取消引用这些嵌套引用。还是不行?
  • 为什么你的数组首先看起来像这样?在你的 Perl 代码中引用东西你可能有点忘乎所以。
  • 我已经添加了解释,希望你能给我一些建议:)
  • 因为 hashrefs 已经是引用,您可能安全地删除了一级引用。

标签: perl reference perl-data-structures template-toolkit


【解决方案1】:

正如 cmets 所说(当我写这篇文章时你自己发现了),你的核心问题是你的哈希被埋得太深了一个多余的引用级别。你应该先努力解决这个问题。

现在回答帖子标题中的实际问题,AFAIK 模板工具包本身并没有提供强制哈希解除引用的工具,但添加一个是可行的:

my @array = ( \{ nice_key => undef, nicer_key => '0', nicest_key => 'Miller'} );

Template->new->process( \<<EOT, { deref => sub{${+shift}}, tablerows => \@array } );
[% FOREACH row = tablerows %]
    <tr>
        <td>[% row %]</td>
        <td>[% deref(row) %]</td>
        <td>[% deref(row).nicer_key %]</td>
        <td>[% deref(row).nicest_key %]</td>
    </tr>
[% END %]
EOT

我实际上尝试将其实现为标量 vmethod,但失败了。有什么指点吗?

【讨论】:

    【解决方案2】:

    好的,我找到了问题:

    $tabledata{$current_no} = ();
    push @tablerows, \$tabledata{$current_no};
    

    在我的代码中,现在我有

    $tabledata{$current_no} = {};
    push @tablerows, $tabledata{$current_no};
    

    这意味着,我有一个哈希引用,而不是哈希上下文中的列表,而这正是我想要的。

    这会导致以下转储(注意,没有对引用的引用)并且模板被正确解析。

    $VAR1 = {
        'nice_key' => undef,
        'nicer_key' => '0',
        'nicest_key' => 'Miller'
      };
    $VAR2 = {
        'nice_key' => undef,
        'nicer_key' => '0',
        'nicest_key' => 'Farns'
      };
    $VAR3 = {
        'nice_key' => undef,
        'nicer_key' => '0',
        'nicest_key' => 'Woodstock'
      };
    ...
    

    【讨论】:

      猜你喜欢
      • 2014-01-30
      • 2019-05-29
      • 2019-07-12
      • 2012-09-06
      • 2014-05-08
      • 2015-12-07
      • 2012-05-28
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多