One more way.

1
2
3
4
5
6
7
8
9
10
let myProcesses = ["svchost"; "sqlservr"; "opera"]  
let exists(proc) = myProcesses |> List.exists (fun a -> a = proc)

let printProc =     
    System.Diagnostics.Process.GetProcesses()            
    |> Seq.map(fun a -> a.Id, a.ProcessName.ToLower() )    
    |> Seq.filter(fun (id, pname) -> exists(pname))    
    |> Seq.sortBy(fun (id, pname) -> pname, id)    
    |> Seq.iter(fun (id, pname) -> printf "ID : %A, Process:%A\n" id pname)
By on 3/22/2011 4:11 AM ()

Oops, a few characters were missing in my last post, sorry about that.

With respect to your actual question: I think there is nothing wrong with your code. But as always, there are possible improvements, some of which are a matter of taste.

1. I think it is a good idea to introduce a function like "containsIgnoreCase" to make the code more readable. It could even be implemented as an extension method for System.String or for the F# String module if the function is needed often.

2. Combinations of map and filter are sometimes more readable as sequence expressions, especially if the arguments to map and filter are anonymous functions. (List expressions or array expressions are also an alternative, depending on how you want to use the result.)

3. If you work with the (id,name) tuple a lot, you may want to introduce a record for this data structure. In this small snippet that is hardly justified. Just mentioning this for the general case.

So this is a possible alternative way to write it:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
 

open System 

let containsIgnoreCase (str:string) substr =
   str.IndexOf(substr, StringComparison.OrdinalIgnoreCase) >= 0

type ProcessInfo = { Name: string; Id: int }

let processes =
   seq { for p in Diagnostics.Process.GetProcesses() do
            if Seq.exists (containsIgnoreCase p.ProcessName) ["svchost"; "postgres"; "chrome"] then
               yield { Name=p.ProcessName; Id=p.Id }
   } |> Seq.sort

for {Name=pname; Id=pid} in processes do
   printfn "Process Name: %s; Process ID: %A" pname pid
By on 3/20/2011 2:02 PM ()

Reformatted code (using IE 8 or 9 in compatibility mode; with option "Content Editor" set to "HTML Rich Editor (for Developers)" on the profile page in "Site options"):

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
 

// Created on: 3/18/2010 
// processList.fs 
// Code Snippet to match a list running system processes with a lookup list 
// 
open System 

// Define lookup list 
let plistSrch = "svchost postgres chrome" 
let pSrchArray = plistSrch.Split(' ') 

let prslt = 
    System.Diagnostics.Process.GetProcesses() 
    |> Array.map (fun a -> (a.Id , a.ProcessName)) 
    // this is pretty convoluted - there must be an easier/more intuituve way 
    // to filter against a match list 
    |> Array.filter (fun (id, processName) -> 
        pSrchArray |> Array.exists (fun plistSrch -> 
            processName.IndexOf(plistSrch, StringComparison.OrdinalIgnoreCase) >= 0)) 

// Sort by process name 
let sorted = Seq.sortBy (fun (a,b) -> b, a) prslt 

// display results 
for r in sorted do 
    let pid, pname = r 
    //printfn "Process ID: %A; Process Name: %s" pid pname 
    printfn "Process Name: %s; Pr
By on 3/19/2011 3:22 PM ()
IntelliFactory Offices Copyright (c) 2011-2012 IntelliFactory. All rights reserved.
Home | Products | Consulting | Trainings | Blogs | Jobs | Contact Us | Terms of Use | Privacy Policy | Cookie Policy
Built with WebSharper