在NetLogo中动态确定自我和我自己的范围?

时间:2018-02-08 18:25:44

标签: netlogo

当我运行此代码时:

  to myself1
    create-turtles 1 
    let a "a"
    ask turtle 0 [
      show a
      show self
      ask patch-here [
        show a
        show self
        show myself
      ]
    ]
  end

我得到了这个输出:

(turtle 0): "a"
(turtle 0): (turtle 0)
(patch 0 0): "a"
(patch 0 0): (patch 0 0)
(patch 0 0): (turtle 0)

因此,ask patch代码区self内部引用了修补程序,而myself引用了turtle 0

这就是NetLogo用户手册(和示例代码)所期望的。

我不清楚为什么self应该引用补丁而不是turtle 0

不可否认,自从我编写任何Java以来​​已经很长时间了,但我的理解是匿名函数中的this指的是嵌入函数的对象。相比之下,上面代码中的self指的是运行代码的补丁 - 而不是self在词汇上出现的乌龟。此外,可以从代码块中访问本地变量a

决定使代码块本地self,可能是为了提供一种方法来引用正在执行该块的代理,这要求NetLogo定义另一种方式来引用调用上下文。这是myself的函数,如示例输出所示。

更一般地说,即使在单独的函数中使用,myself似乎也会引用调用乌龟。

to myself2
  let a "a"
  ask turtle 0 [
    show a
    show self
    ask patch-here [ myself2' ]   
  ]
end

to myself2'
  ; show a
  show self    
  show myself
end

输出结果为:

(turtle 0): "a"
(turtle 0): (turtle 0)
(patch 0 0): (patch 0 0)
(patch 0 0): (turtle 0)

因此可以从单独的函数访问myself并返回调用乌龟。但似乎相似的变量a无法访问。如果show a未被注释掉,NetLogo会发出一条错误消息,指出a中未定义myself2'。 (换句话说,NetLogo一般不会实现动态范围,即使这些示例似乎表明它适用于selfmyself。)

所以,对不起长时间的预备。我的问题是关于解释用于selfmyself的准动态范围的最佳方法,而不是用于a等局部变量。公平地说selfmyself只是 ad hoc 特殊情况,还是有更好的方式来讨论它?

1 个答案:

答案 0 :(得分:0)

很棒的问题。

selfmyself所代表的概念根本不存在于其他编程语言中。其他编程语言没有“#34;代理执行此代码的概念”,因为这些语言首先不是基于代理的。

OO语言中与this的任何类比都是最好的,并且在最坏的情况下会产生误导。

selfmyself在定义时非常有用,如果它们没有出现在语言中,并且有定义,那么您在尝试编码各种各样的东西。这是我能给出的最好的简短答案,为什么他们被定义为:他们有用。

至于a等局部变量的范围行为,我认为这是一个单独的问题。您当然可以想象尝试提出某种基于代理的局部变量定义,其中a类似于临时创建代理变量。对我而言,这样的设计是否可行或甚至是可取的并不是显而易见的,但无论如何,我们并没有这样做,我认为我们甚至没有认真研究过这种可能性

NetLogo中的局部变量与其他词法范围的语言中的局部变量完全相同。他们没有参与基于代理的语言性质。