2013-08-17 36 views
1

我正在玩一個簡單的f#示例this nice tutorial。並遇到這個非常奇怪的錯誤。在向webrequest添加代理後,它告訴我類型WebProxy與預期類型IWebProxy不兼容。這有點奇怪,爲什麼我的C#錘子在F#中沒有工作?這個表達式預計有IWebProxy類型,但這裏有類型WebProxy

我在這裏做錯了什麼?

let downloadUrlToFile url file = 
    let req = WebRequest.Create(Uri(url)) 
    req.Proxy = new WebProxy("127.0.0.1", 444) 
    use res = req.GetResponse() 
    use stream = res.GetResponseStream() 
    use reader = new IO.StreamReader(stream) 
    let timestamp = DateTime.UtcNow.ToString("yyy-MM-dd") 
    let path = sprintf "%s.%s.html" file timestamp 
    use writer = new IO.StreamWriter(path) 
    writer.Write(reader.ReadToEnd()) 
    printfn "done loading %s to %s" url file 

錯誤消息

This expression was expected to have type 
    IWebProxy  
but here has type 
    WebProxy  

回答

3

正如其他人已經解釋過,問題是=是比較操作。在這種情況下,您需要一個作業,即<-

但是,在幾種情況下,F#實際上會隱式執行upcasts,而賦值就是其中之一,因此您不需要添加:> IWebProxy來投射對象。以下將工作得很好:

req.Proxy <- new WebProxy("127.0.0.1", 444) 

除了賦值,F#還向方法或函數傳遞參數時隱式上傳。它不會爲比較運算符做這件事(因爲您想知道,沒有任何含糊之處,哪些類型被比較。)

1

嗯,至少有兩件事情,你不要指望在這裏:

  • req.Proxy = new WebProxy(...)是一個比較,你可能想req.Proxy <- new WebProxy(...)代替。
  • F#不會自動上傳。因此,您可能需要執行類似req.Proxy <- new WebProxy(...) :> _的靜態上傳。這告訴F#「上傳到任何適合的地方」。

(我沒有實際運行你的代碼,所以你可能有更多的問題,但是這兩個肯定是一個C#程序員很重要的。)

1

F#不自動向上轉型值如C#做,所以你需要顯式轉換WebProxy對象IWebProxy,像這樣:

req.Proxy <- WebProxy("127.0.0.1", 444) :> IWebProxy 

同樣重要:F#中分配語法<-,不=爲C#。如果你使用=,你會得到一個錯誤信息是這樣的:

Type constraint mismatch. The type 
    bool  
is not compatible with type 
    IWebProxy  
The type 'bool' is not compatible with the type 'IWebProxy' 
相關問題