3 people like it.

Calculate left margins

Take some text and work out where the left margins are, returning the most common margin settings first. Useful for processing somewhat messy text items like movie scripts. Left margins are defined by leading spaces. Tabs must be expanded before calling.

 1: 
 2: 
 3: 
 4: 
 5: 
 6: 
 7: 
 8: 
 9: 
10: 
11: 
12: 
13: 
14: 
15: 
16: 
17: 
18: 
19: 
20: 
21: 
22: 
23: 
let margins (lines : seq<string>) =
    let marginWidth (line : string) =
        line.Length - line.TrimStart([|' '|]).Length 
    lines
    |> Seq.map (fun line -> marginWidth line)
    |> Seq.countBy (fun width -> width)
    |> Seq.filter (fun margCount -> fst(margCount) > 0)
    |> Seq.sortBy (fun margCount -> -snd(margCount))

// Example:
let lines = [
                "This has no margin."
                " This has a one-space margin."
                " So does this."
                "      These three lines have a six-space margin."
                "      Again with the six-space margin."
                "      And again."
                " Back to one space."
                "      And finally, another six space."
            ]

// Output: seq [(6, 4); (1, 3)]
lines |> margins
val margins : lines:seq<string> -> seq<int * int>

Full name: Script.margins
val lines : seq<string>
Multiple items
val seq : sequence:seq<'T> -> seq<'T>

Full name: Microsoft.FSharp.Core.Operators.seq

--------------------
type seq<'T> = System.Collections.Generic.IEnumerable<'T>

Full name: Microsoft.FSharp.Collections.seq<_>
Multiple items
val string : value:'T -> string

Full name: Microsoft.FSharp.Core.Operators.string

--------------------
type string = System.String

Full name: Microsoft.FSharp.Core.string
val marginWidth : (string -> int)
val line : string
property System.String.Length: int
System.String.TrimStart([<System.ParamArray>] trimChars: char []) : string
module Seq

from Microsoft.FSharp.Collections
val map : mapping:('T -> 'U) -> source:seq<'T> -> seq<'U>

Full name: Microsoft.FSharp.Collections.Seq.map
val countBy : projection:('T -> 'Key) -> source:seq<'T> -> seq<'Key * int> (requires equality)

Full name: Microsoft.FSharp.Collections.Seq.countBy
val width : int
val filter : predicate:('T -> bool) -> source:seq<'T> -> seq<'T>

Full name: Microsoft.FSharp.Collections.Seq.filter
val margCount : int * int
val fst : tuple:('T1 * 'T2) -> 'T1

Full name: Microsoft.FSharp.Core.Operators.fst
val sortBy : projection:('T -> 'Key) -> source:seq<'T> -> seq<'T> (requires comparison)

Full name: Microsoft.FSharp.Collections.Seq.sortBy
val snd : tuple:('T1 * 'T2) -> 'T2

Full name: Microsoft.FSharp.Core.Operators.snd
val lines : string list

Full name: Script.lines
Raw view Test code New version

More information

Link:http://fssnip.net/9K
Posted:12 years ago
Author:Kit Eason
Tags: margins text