2014-01-28 2 views
3

두 개의 에이전트 세트와 명령 블록을 사용하는 프리미티브를 작성하고 있습니다. 몇 가지 함수를 호출하고 현재 컨텍스트에서 명령 블록을 실행 한 다음 다른 함수를 호출해야합니다. 여기에 지금까지이 작업은 다음과 같습니다NetLogo 확장자의 프리미티브에서 명령 블록을 실행하십시오.

class WithContext(pushGraphContext: GraphContext => Unit, popGraphContext: api.World => GraphContext) 
    extends api.DefaultCommand { 
    override def getSyntax = commandSyntax(
    Array(AgentsetType, AgentsetType, CommandBlockType)) 

    def perform(args: Array[Argument], context: Context) { 
    val turtleSet = args(0).getAgentSet.requireTurtleSet 
    val linkSet = args(1).getAgentSet.requireLinkSet 
    val world = linkSet.world 
    val gc = new GraphContext(world, turtleSet, linkSet) 
    val extContext = context.asInstanceOf[ExtensionContext] 
    val nvmContext = extContext.nvmContext 
    pushGraphContext(gc) 
    // execute command block here 
    popGraphContext(world) 
    } 
} 

나는 nvmContext.runExclusively를 사용하는 몇 가지 예를 보였다, 그러나 주어진 agentset 명령 블록을 실행할 필요를 위해 특별히처럼 그 보였다. 나는 현재 에이전트 (아마도 관찰자)가 그것을 실행하기를 원한다. 에이전트 세트에서 nvm.agent을 랩핑하고이를 nvmContext.runExclusively으로 전달해야합니까? 그렇다면 에이전트 세트에서 에이전트를 랩핑하는 가장 쉬운 방법은 무엇입니까? 그렇지 않다면 어떻게해야합니까?

답변

2

방법 # 1

빠를 - 뷰트 틀림-더러운 방법 (예를 들면)에서 https://github.com/NetLogo/Sample-Scala-Extension/blob/master/src/SampleScalaExtension.scalacreate-red-turtles 명령 있듯이, runExclusiveJob을 사용하는 것이다.

에이전트 세트에서 현재 에이전트를 랩핑하려면 agent.AgentSetBuilder을 사용할 수 있습니다. (당신은 또한 ArrayAgentSet 생성자 중 하나에 길이 1의 Array[Agent]을 통과 할 수 있지만,이 변경 될 수 있습니다 내부 구현 세부 사항에 덜 의존 이후 나는 AgentSetBuilder를 권 해드립니다.)

방법 # 2

방법 # 1의 단점은 추가 AgentSet, JobContext 개체를 만들고 설정하고이를 통해 실행을 지시하는 것과 관련된 약간의 일정한 오버 헤드입니다.

별도의 작업 생성 및 실행은 실제로 ifwhile과 같은 내장 명령이 작동하는 방식이 아닙니다. 새 작업을 만드는 대신 현재 작업에 남아 명령 포인터 (nvm.Context.ip)를 조작하여 명령 블록의 명령을 실행 (또는 실행하지 않음)하여 건너 뛰거나 건너 뜁니다.

확장 명령이 동일한 기능을 수행 할 수 있다고 생각합니다. 이전에 시도했는지 확실하지 않지만 작동하지 않을 이유는 없습니다.

이렇게하면 https://github.com/NetLogo/NetLogo/wiki/Engine-architecture에 문서화 된대로 NetLogo 엔진 내부에 대해 더 많이 이해하게됩니다. 예를 들어 프리미엄을 모델링합니다. https://github.com/NetLogo/NetLogo/blob/5.0.x/src/main/org/nlogo/prim/etc/_if.java이고 구현 변경은 nvm.CustomAssembled입니다. 확장 명령을 실행하는 prim._extern은 해당 assemble 메서드를 래핑 된 명령 자체의 assemble 메서드에 위임합니다. 따라서 assemble 메서드에서는 작업을 종료하기 위해 끝에 done() 메서드를 호출하는 대신 실행을 통해 가을.

나는이 방법으로 작동하는 예제를 만들려고했지만 몇 시간이 걸렸습니다. 진짜 필요가 없다면 저에게 가치있는 일은 아닐 것입니다.

+0

'agent.AgentSetBuilder'가 더 이상 존재하지 않습니다. 즉, ArrayAgentSet (클래스 [? extends 에이전트], Array [에이전트], 월드)'ArrayAgentSet'의 생성자를 사용하는 것은 쉽습니다. –

+1

아, 죄송합니다, 'AgentSetBuilder'는 마스터/헤드리스 물건입니다. 5.0.x 환경에서 네가 옳은 일을하고있다. –

관련 문제