I'm testing the following code to populate a dictionary recursively. However the type inference does not seem to recognize the dictionary type. I've tried using a type annotation but that did not seem to help.
Are there some restrictions on the use of dictionaries in a recursive routine. Do I need to make the dictionary mutable since I expect to change it during iterations.
open System
open System.Collections.Generic
////dictionary recursion test
let pop_dict tlist =
// let rec inner tlist acc ddict:Dictionary<string,int> =
let rec inner tlist acc ddict =
match tlist with
| [] -> ddict.Add ("dummykey", acc)
| x::xs -> inner xs (x::acc) ddict
let ddict = Dictionary<string,int>()开发者_StackOverflow
inner tlist [] ddict
// Main Entry Point
let main() =
let tlist = [1;2;3;4]
let d = pop_dict tlist
main()
First of all, your types don't match up.
You're trying to add an int list
(which is what acc
is) to a dictionary that is supposed to contain int
s.
Apart from that, however, the reason that the compiler cannot infer the type of ddict
is. Remember, when the type checker determines types for the function, it doesn't look at what it gets called with later. It only has the following information available:
let rec inner tlist acc ddict =
match tlist with
| [] -> ddict.Add ("dummykey", acc)
| x::xs -> inner xs (x::acc) ddict
That means, that the only information it knows about ddict
when it compiles the function, is that it has a method named Add
, which string * 'a list -> ?
.
To fix it, change
let rec inner tlist acc ddict =
to
let rec inner tlist acc (ddict:Dictionary<string,int>) =
You still have the trouble with the mismatching types on the dictionary, however, so you probably want it to be Dictionary<string, int list>
, if you plan on storing int list
s in it.
is that what you wanted?
let pop_dict tlist =
let rec inner tlist acc (ddict:Dictionary<string,int list>) =
match tlist with
| [] -> ddict.Add ("dummykey", acc)
| x::xs -> inner xs (x::acc) ddict
let ddict = Dictionary<string,int list>()
inner tlist [] ddict
// Main Entry Point
let main() =
let tlist = [1;2;3;4]
let d = pop_dict tlist
()
精彩评论