2013-02-26 6 views
2

У меня есть F # 3,0 агент, завернутые в классе:F # странный агент переинициализировать поведение

type AgentWrapper() = 
    let myAgent = Agent.Start(fun inbox -> 
      let rec loop (state: int) = 
       async { 
        let! (replyChannel: AsyncReplyChannel<int>) = inbox.Receive() 
        let newState = state + 1 
        replyChannel.Reply newState 
        return! loop newState 
       } 
      loop 0) 

    member private this.agent = myAgent 

    member this.Send() = 
     this.agent.PostAndReply (fun replyChannel -> replyChannel) 

Когда я посылать ему сообщения следующим образом:

let f = new AgentWrapper() 
f.Send() |> printf "Reply: %d\n" 
f.Send() |> printf "Reply: %d\n" 
f.Send() |> printf "Reply: %d\n" 

я получаю ожидаемый ответов:

Reply: 1 
Reply: 2 
Reply: 3 

Однако, если я удаляю привязку let для агент и непосредственно присвоить его this.agent собственности:

type AgentWrapper() = 

    member private this.agent = Agent.Start(fun inbox -> 
      let rec loop (state: int) = 
       async { 
        let! (replyChannel: AsyncReplyChannel<int>) = inbox.Receive() 
        let newState = state + 1 
        replyChannel.Reply newState 
        return! loop newState 
       } 
      loop 0) 

    member this.Send() = 
     this.agent.PostAndReply (fun replyChannel -> replyChannel) 

Я тогда получить ответы:

Reply: 1 
Reply: 1 
Reply: 1 

Я смотрел на это в течение нескольких часов, и я не могу понять, почему агент получает повторную инициализацию каждый раз, когда я вызываю AgentWrapper.Send. Это похоже на this.agent получает переназначение каждый раз, когда я его называю (т. Е. Действует как метод, а не свойство). Что мне не хватает?

ответ

3

Он чувствует, как this.agent становится переназначен каждый раз, когда я называю его (т.е. действует как метод, а не свойство). Что мне не хватает?

Это именно то, что происходит, и документируется в спецификации (соответствующая часть от 18.13.1 следует)

Статические и экземпляра члены собственности оцениваются каждый раз, когда член вызывается. Например, в следующем, тело элемента вычисляется каждый раз, когда C.Time оценивают следующим образом:

типа С() =

static member Time = System.DateTime.Now 

Это analgous к вашей ситуации

+0

Doh! Сегодня я бегаю «глупо» ... спасибо. – Akash

Смежные вопросы