3 people like it.
Like the snippet!
.NET 1.1 collections in F#
Even with the latest tools, we're sometimes exposed to .NET archeaology: parts of the framework designed before .NET 2. Examples of this are the dictionary classes from System.Collections, which are a little strongly typed, but not quite -- you see them if you call HttpUtility.ParseQueryString, or if you use pretty much anything in System.Configuration. Here's some code to make these classes a little safer in F#.
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
21:
22:
23:
24:
25:
26:
27:
28:
29:
30:
31:
32:
33:
34:
35:
|
open System.Collections
let inline pairs (collection : ^c when ^c :> IEnumerable and ^c : (member get_Item : 'a -> 'b)) : seq<'a * 'b> =
seq {
match collection.GetEnumerator() with
| :? IDictionaryEnumerator as en ->
while en.MoveNext() do
yield unbox en.Key, unbox en.Value
| en ->
while en.MoveNext() do
let key = unbox en.Current
let value = (^c : (member get_Item : 'a -> 'b) (collection, key))
yield key, value
}
#r "System.Web"
open System.Collections.Specialized
open System.Web
for key, value in pairs (HttpUtility.ParseQueryString("hello=world&hello=tim&fsharp=cool")) do
printfn "%s = %s" key value
let ht = Hashtable()
ht.["hello"] <- "world"
ht.["fsharp"] <- "cool"
for key, value in pairs ht do
printfn "%s = %s" (unbox key) (unbox value)
let nvc = NameValueCollection()
nvc.["hello"] <- "world"
nvc.["fsharp"] <- "cool"
for key, value in pairs nvc do
printfn "%s = %s" key value
|
namespace System
namespace System.Collections
val pairs : collection:'c -> seq<'a * 'b> (requires 'c :> IEnumerable and member get_Item)
Full name: Script.pairs
val collection : 'c (requires 'c :> IEnumerable and member get_Item)
type IEnumerable =
member GetEnumerator : unit -> IEnumerator
Full name: System.Collections.IEnumerable
Multiple items
val seq : sequence:seq<'T> -> seq<'T>
Full name: Microsoft.FSharp.Core.Operators.seq
--------------------
type seq<'T> = Generic.IEnumerable<'T>
Full name: Microsoft.FSharp.Collections.seq<_>
IEnumerable.GetEnumerator() : IEnumerator
type IDictionaryEnumerator =
member Entry : DictionaryEntry
member Key : obj
member Value : obj
Full name: System.Collections.IDictionaryEnumerator
val en : IDictionaryEnumerator
IEnumerator.MoveNext() : bool
val unbox : value:obj -> 'T
Full name: Microsoft.FSharp.Core.Operators.unbox
property IDictionaryEnumerator.Key: obj
property IDictionaryEnumerator.Value: obj
val en : IEnumerator
val key : 'a
property IEnumerator.Current: obj
val value : 'b
namespace System.Collections.Specialized
namespace System.Web
val key : string
val value : string
Multiple items
type HttpUtility =
new : unit -> HttpUtility
static member HtmlAttributeEncode : s:string -> string + 1 overload
static member HtmlDecode : s:string -> string + 1 overload
static member HtmlEncode : s:string -> string + 2 overloads
static member JavaScriptStringEncode : value:string -> string + 1 overload
static member ParseQueryString : query:string -> NameValueCollection + 1 overload
static member UrlDecode : str:string -> string + 3 overloads
static member UrlDecodeToBytes : str:string -> byte[] + 3 overloads
static member UrlEncode : str:string -> string + 3 overloads
static member UrlEncodeToBytes : str:string -> byte[] + 3 overloads
...
Full name: System.Web.HttpUtility
--------------------
HttpUtility() : unit
HttpUtility.ParseQueryString(query: string) : NameValueCollection
HttpUtility.ParseQueryString(query: string, encoding: System.Text.Encoding) : NameValueCollection
val printfn : format:Printf.TextWriterFormat<'T> -> 'T
Full name: Microsoft.FSharp.Core.ExtraTopLevelOperators.printfn
val ht : Hashtable
Full name: Script.ht
Multiple items
type Hashtable =
new : unit -> Hashtable + 14 overloads
member Add : key:obj * value:obj -> unit
member Clear : unit -> unit
member Clone : unit -> obj
member Contains : key:obj -> bool
member ContainsKey : key:obj -> bool
member ContainsValue : value:obj -> bool
member CopyTo : array:Array * arrayIndex:int -> unit
member Count : int
member GetEnumerator : unit -> IDictionaryEnumerator
...
Full name: System.Collections.Hashtable
--------------------
Hashtable() : unit
Hashtable(capacity: int) : unit
Hashtable(equalityComparer: IEqualityComparer) : unit
Hashtable(d: IDictionary) : unit
Hashtable(capacity: int, loadFactor: float32) : unit
Hashtable(capacity: int, equalityComparer: IEqualityComparer) : unit
Hashtable(d: IDictionary, loadFactor: float32) : unit
Hashtable(d: IDictionary, equalityComparer: IEqualityComparer) : unit
Hashtable(capacity: int, loadFactor: float32, equalityComparer: IEqualityComparer) : unit
Hashtable(d: IDictionary, loadFactor: float32, equalityComparer: IEqualityComparer) : unit
val key : obj
val value : obj
val nvc : NameValueCollection
Full name: Script.nvc
Multiple items
type NameValueCollection =
inherit NameObjectCollectionBase
new : unit -> NameValueCollection + 7 overloads
member Add : c:NameValueCollection -> unit + 1 overload
member AllKeys : string[]
member Clear : unit -> unit
member CopyTo : dest:Array * index:int -> unit
member Get : name:string -> string + 1 overload
member GetKey : index:int -> string
member GetValues : name:string -> string[] + 1 overload
member HasKeys : unit -> bool
member Item : string -> string with get, set
...
Full name: System.Collections.Specialized.NameValueCollection
--------------------
NameValueCollection() : unit
NameValueCollection(col: NameValueCollection) : unit
NameValueCollection(capacity: int) : unit
NameValueCollection(equalityComparer: IEqualityComparer) : unit
NameValueCollection(capacity: int, equalityComparer: IEqualityComparer) : unit
NameValueCollection(capacity: int, col: NameValueCollection) : unit
More information