for 什么时候调用迭代器方法?

When does for call the iterator method?

这道题 , but seems to reveal a different problem with mixins (or a different misunderstanding of the syntax on my part). What Iterable 做的是让一个数据结构有效地迭代,也就是说,你可以通过在它前面加上 for.

来创建循环

Iterable serves as an API for objects that can be iterated with the for construct and related iteration constructs, like hyper operators.

所以让我们尝试将其付诸实践:

 my &logger = -> $event  {
    state %store;
    if ( $event ) {
        %store{ DateTime.new( now ) } = $event;
    } else {
        %store;
    }
}

role Forable does Iterable {
    method iterator(&self:) {
        self( Nil );
    }
}

logger( "One" );
logger( "Two" );

&logger does Forable;

.say for &logger;

这根本行不通; say 作为简单项目应用于 &logger。但是,如果我们将最后一句话更改为:

.say for &logger.iterator;

我猜这表明该角色实际上在起作用,并且混入了。由于&logger的类型是Block+{Forable},如果不直接混入Iterable,它可能不起作用。事实上,从 Forable 声明中删除 does Iterable 不会以任何方式影响它。让我们试试这个:

&logger does (Iterable,Forable);

现在 &logger 的类型显示为 Block+{Iterable,Forable},但仍然没有喜悦。 iterator 必须直接调用。知道如何解决这个问题吗?

我认为你做不到。基本问题是 &fooCallable 对象)和 foo()(调用 Callable 对象)是两个截然不同的东西。

我觉得你正在尝试将 method 添加到 class,但你正在使用 Sub

您需要在 logger 的 return 值上混入 iterator 方法。因为我不太明白你想要达到什么目的,所以很难回答这个问题。

看着你显然想要实现的结果,我想到了这个:

my %store;
multi sub logger() {
    %store
}
multi sub logger($event) {
    %store{ DateTime.new( now ) } = $event;
}

logger( "One" );
logger( "Two" );

.say for logger;

但这根本不使用 roles。所以这可能不是你想要的。

When does for call the iterator method?

据我了解,如果迭代功能的 () 参数是一个 Scalar 容器,那么它将使用容器中的值而不调用 .iterator。否则,它会对其调用 .iterator,如果它是表达式或例程调用,则首先对其求值。


&logger does Forable;
.say for &logger;

This simply does not work; say is applied to &logger as a simple item.

& 是一个名词标记(sigil),标记 Callable 本质上是一个事物,一个代码块。

更具体地说,&logger 绑定到类型为 CallableScalar 容器,与 $logger 完全相同(带有 $ 印记) 如果你写 my Callable $logger:

say .WHAT, .VAR, .VAR.WHAT, .VAR.of
for my &logger, my Callable $logger

显示:

(Callable)Callable(Scalar)(Callable)
(Callable)Callable(Scalar)(Callable)

Since the type for &logger is Block+{Forable}

实际上 Callable 的类型 包含在 绑定到 &loggerScalar 容器中。

不是 &logger 容器本身的类型,它是 Scalar,如上所示。

当以变量的形式给出单个参数时,for 等迭代功能会查看变量,而不是变量中包含的值,看看它是否是 IterableScalar 不是 Iterable.

Any idea on how to solve this?

请参阅 lizmat 对一种方法的回答。