如何让一只乌龟能够在 Netlogo 中保存其他乌龟 ID?

Posted

技术标签:

【中文标题】如何让一只乌龟能够在 Netlogo 中保存其他乌龟 ID?【英文标题】:How to make a turtle able to save other turtles ID in Netlogo? 【发布时间】:2018-09-28 07:18:43 【问题描述】:

这是我想做的:

    我想要一个 团队,由 3 只海龟组成一组

    所有海龟都需要将自己的 ID 和 teammatesID 存储在名为 teammatesID 的变量中。 (想象一下你要创建一个组,你会把你的名字和你朋友的名字放在一个列表中,这就是为什么这个变量需要存储 ownID,我不好解释......) p>

    我需要他们能够显示所有队友 ID,而不是只显示 (agentset,3 turtles)

    他们集齐所有 3 名成员后,他们将收到 teamID

这里的问题是我不知道如何让这些海龟将自己的 ID 和 teammatesID 存储在名为 teammatesID 的变量中。在一个组中,他们应该有3个不同的成员。这些队友应该来自同一组。以及如何给予他们teamID @987654324 @他们获取所有成员

这是我的代码:

global
[ teamID]

turtles-own
[
  myID
  teammatesID
]

to setup
  clear-all
  set-default-shape turtles "arrow"
  create-turtles 10

  ask turtles [ set myID who]
  reset-ticks
  setup-group
end

to setup-group

   set teamID []
   let agent one-of other turtles
   let  nearestNeighbor one-of other turtles in-radius 1 
   set teamID = 0
   ask agent with [ teammatesID < 3]
   [ ask nearestNeighbor with [teammatesID < 3]
     [ ;set teammatesID = myID ; here is the problem, I need to make sure they did not save the same turtle in one group.
       show teammatesID]]

       ask agent with [teammatesID > 3]
       set teamID fput teamID teamID
        end

感谢您在这里的额外时间。谢谢。

【问题讨论】:

你能解释一下你所说的“这些队友不应该来自同一个小组吗?小组和团队在这里是不同的东西吗? 根据我的编码,条件是“少于 3 个成员的海龟需要寻找其他成员”。例如,乌龟 1 和乌龟 2 创建了一个团队,所以乌龟 1 的队友 ID 应该有他的 ID 和乌龟 2 的 ID,乌龟 2 也是如此,它有自己的 ID 和乌龟 1 的 ID。但是,他们俩还需要再找一个成员,并且他们都满足我之前说的条件,即他们都少于3个成员,我不希望他们最终在他们的团队中找到相同的乌龟,这将最终 => 龟 1 有自己的 ID,和双龟 2 ID。很抱歉我的错误解释 【参考方案1】:

如果团队是随机的,我认为您不需要为此设置循环,因为 ask 无论如何都会以随机顺序调用海龟。

我认为您仍然应该在这里使用代理集,因为它使某些事情变得更容易。例如,一旦海龟知道了它们的(agentset,3 turtles),您就可以轻松地查询该代理集以获取myIDs 或您所追求的任何变量。

我并不完全清楚 teamID 的目的,所以我可能会在这里偏离基础,但如果 teamIDs 对每个组都是唯一的,我认为你不希望它作为全局变量三只乌龟。您可能还希望它是 turtles-own 变量。

这是一个结合了上述想法的示例。使用此设置:

turtles-own [ myteamset teamID myID teammatesID ]

to setup 
  ca
  crt 10 [
    set myID who
    set myteamset nobody 
    set teammatesID [ ]
  ]
  setup-groups
  print remove-duplicates [teammatesID] of turtles
  print sort [teamID] of turtles
  reset-ticks
end

还有setup-groups 过程(cmets 中有更多详细信息):

to setup-groups
  ask turtles [
    ; If you don't have a team yet
    if myteamset = nobody [
      ; Make a temporary agent-set out of all other turtles that
      ; are also not yet part of a team
      let possible-teammates other turtles with [ myteamset = nobody ]

      ; If there are at least two more turtles, make a new team:
      ifelse count possible-teammates > 1 [
        ; Make a team out of myself and two possible teammates
        set myteamset ( turtle-set self n-of 2 possible-teammates )

        ; Make a temporary variable to pass on to my entire team
        ; (yourself included) for the team ids and the team members.
        ; Also, assign a random teamID to the whole team
        let ids sort [myID] of myteamset
        let teammmembers myteamset
        let tempteam random 1000
        ask myteamset [
          set teammatesID ids
          set myteamset teammmembers
          set teamID tempteam
        ]
      ] [
        ; If there aren't enough turtles to form a new team, 
        ; print a warning to the console.
        show "Not enough turtles to make a new team!"
      ]
    ]
  ]
end

如果这就是你所追求的,请告诉我,希望对你有所帮助。

编辑 - 根据您的 cmets:

要获得连续的团队编号,您可以使用一个简单的计数器,该计数器被分配给一个团队,然后为下一个增加,修改后的setup-groups 看起来像:

to setup-groups
  ; Create a temporary variable to use as a counter
  let teamCounter 1
  ask turtles [
    if myteamset = nobody [
      let possible-teammates other turtles with [ myteamset = nobody ]
      ifelse count possible-teammates > 1 [
        set myteamset ( turtle-set self n-of 2 possible-teammates )
        let ids sort [myID] of myteamset
        let teammmembers myteamset

        ; Assign the current teamCounter as team number, then 
        ; increment it by one for the next team
        let tempteam teamCounter
        set teamCounter teamCounter + 1
        ask myteamset [
          set teammatesID ids
          set myteamset teammmembers
          set teamID tempteam
        ]
      ] [
        show "Not enough turtles to make a new team!"
      ]
    ]
  ]
end

第二个问题可能值得单独提出一个新问题,具体取决于您希望获得的深度,但这是一种非常简单的方法,您只需获取所有唯一的团队 ID 并让一只乌龟具有该 ID让他们的团队一起行动:

to move-in-groups
  ; Get the unique team IDs
  let teamNumbers remove-duplicates [teamID] of turtles 

  ; Get one member of each team to ask all members
  ; of its team (itself included) to move 
  foreach teamNumbers [
    tn ->
    ask one-of turtles with [ teamID = tn ] [
      let newHeading heading + random 60 - 30
      if myteamset != nobody [
        ask myteamset [
          set heading newHeading
          fd 1
        ]
      ]
    ]
  ]
end

编辑 2:NetLogo 5 友好版本

to move-in-groups
  ; Get the unique team IDs
  let teamNumbers remove-duplicates [teamID] of turtles

  ; Get one member of each team to ask all members
  ; of its team (itself included) to move
  foreach teamNumbers [
    ask one-of turtles with [ teamID = ? ] [
      let newHeading heading + random 60 - 30
      if myteamset != nobody [
        ask myteamset [
          set heading newHeading
          fd 1
        ]
      ]
    ]
  ]
end

【讨论】:

对,对,对~!哦,我的天哪,这是我打算做的,非常感谢你h~!ヽ(^o^)ノ这对我帮助很大。我已经绞尽脑汁一个星期来解决这个问题。顺便说一句,如果我想将 teamID 设为 1、2、3 ...,我该怎么做?我希望他们在一个小组中移动,我该如何“问”他们? @linda - 乐于助人!我进行了一些修改以可能解决您的 cmets,但如果您的运动需求更深入,您可能最终想问一个新问题。 抱歉回复晚了,to move-in-groups函数中tn是干什么用的?如何设置此变量?我已将tn 更改为团队编号,但to go 代码有问题。·´¯(&gt;▂&lt;)´¯·.·。谢谢你的时间:D @linda - tn 变量是一个临时变量,仅存在于 foreach 块中。您不能设置它,它会代替当前的 teamNumber,因为 foreach 过程会遍历 @987654342 中的每个项目@ 列表。查看foreach 字典条目,了解有关匿名过程如何工作的更多信息。 move-in-groups as-is 对我有用,可以将海龟组作为一个单元移动 - 尝试直接在 go 中调用它,而不需要任何 ask turtles 或其他命令。 感谢编辑的版本5,也感谢组团搬家,这个和我想要的很像,但是我需要agent用植绒规则组团搬家。稍后我将在一个新问题中提问。非常感谢您之前的帮助:D【参考方案2】:

我同意 Luke 的观点,即与团队打交道最合适的方式是作为代理集,而不是复杂的标识符分配。这就是代码的样子。请注意,我没有解决您问题的运动部分。

globals [max-teamsize]

turtles-own
[ teamID
  teammates
]

to testme
  clear-all
  create-turtles 100
  [ setxy random-xcor random-ycor
    set teamID 0
    set teammates nobody
  ]
  set max-teamsize 3
  setup-groups
  reset-ticks
end

to setup-groups
  ; assign turtles to team by allocating a team number
  let counter 1
  ask turtles
  [ if teamID = 0
    [ set teamID counter
      let potential-teammates turtles with [teamID = 0]
      ask n-of min (list (max-teamsize - 1) (count potential-teammates)) potential-teammates
      [ set teamID counter
      ]
      set counter counter + 1
    ]
  ]
  ; store teammates as agentset of other turtles in team
  ask turtles
  [ set teammates other turtles with [teamID = [teamID] of myself]
  ]
end

【讨论】:

首先,感谢您花时间解释这一点,我有一些关于代码的问题,如果它不给您带来负担,您能向我解释一下这部分吗ask n-of min (list (max-teamsize - 1) (count potential-teammates)) potential-teammates。这个是如何工作的?由于我需要显示队友列表来证明我的代码是正确的,所以我坚持显示队友ID等是错误的,从而使turtles-own有很多标识符。非常感谢您的宝贵时间。 ask n-of N agentset 表示从命名的代理集中随机选择 N 个代理。在这段代码中,我将min (list (max-teamsize - 1) (count potential-teammates) 设为 N,因此它会计算所需队友中较小的一个,以及仍需分配的海龟数量。他们被选中的agentset是名为potential-teammates的agentset,它是所有以0为teamID的海龟(因此尚未分配)。 意思是,它可以有一个少于3个成员的组? 是的。如果您有 20 只海龟,并且您已将团队规模设置为 3,则有 6 支 3 人团队可以让您达到 18 只海龟,但只剩下 2 只,因此第 7 队只有 2 名成员 我怎样才能让代理集包括我自己从这里set teammates other turtles with [teamID = [teamID] of myself],我试过set myteam turtle-set self other turtles with [teamID = [teamID] of myself],但它是错误的。还有一个问题,除了脸还有什么其他选择,如果我想让乌龟停留在某个补丁上,如果我使用ask teammates,例如:set food food-quality set location patch-here] face location ,认为我在一年后仍然坚持编写这个程序:'(

以上是关于如何让一只乌龟能够在 Netlogo 中保存其他乌龟 ID?的主要内容,如果未能解决你的问题,请参考以下文章

NetLogo - 如何显示海龟的当前坐标

从嵌套的ask中设置turtle的变量

ROS通过图形化界面控制和查看小乌龟参数

NetLogo-如何将平衡的化学方程式放入模型中?

一只乌龟

我可以将 NetLogo 中的图片保存到 Excel 文件中吗?