1 people like it.

Simple console bar chart

Creates a simple bar chart from a list consisting of a tuple (title:string * value:'a).

 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: 
type Width =
    /// Use the full width of the console
    | FullWidth
    /// The width of the chart including the printed title and value
    | Width of int
    member self.Value =
        match self with
        | FullWidth -> System.Console.WindowWidth
        | Width value -> value

// based on: https://www.daniweb.com/programming/software-development/code/238532/very-simple-console-barchart
let inline drawBarChartWith (width: Width) valueFormatter (xs: (string * 'a) seq) =
    let xs = xs |> Seq.cache
    // calculate maximum of the data
    let maxTitleWidth = xs |> Seq.map (fst >> String.length) |> Seq.max
    let maxValue = xs |> Seq.map snd |> Seq.max
    let maxValueWidth = xs |> Seq.map (snd >> valueFormatter >> String.length) |> Seq.max
    // use full width of console
    let factor = float (width.Value - maxTitleWidth - maxValueWidth - 3)
    // draw chart
    let emptyTitle = String.replicate maxTitleWidth " "
    let emptyValue = String.replicate maxValueWidth " "
    printfn "%s%s│" emptyTitle emptyValue
    for (title, value) in xs do
        let paddedTitle = (string title).PadLeft(maxTitleWidth)
        let width = int (float value / float maxValue * factor)
        let value = (valueFormatter value).PadLeft(maxValueWidth)
        let segments = String.replicate width "■"
        printfn "%s%s%s" paddedTitle value segments
    printfn "%s%s│" emptyTitle emptyValue

let inline drawBarChart xs =
    drawBarChartWith FullWidth string xs
  • Usage example:
1: 
2: 
3: 
4: 
5: 
6: 
7: 
8: 
9: 
open FSharp.Data

let data = WorldBankData.GetDataContext()
let idc = data.Countries.Italy.Indicators.``Agricultural land (% of land area)``
let yearsWithValues = Seq.zip idc.Years idc.Values

yearsWithValues
|> Seq.map (fun (x, y) -> string x, y)
|> drawBarChartWith (Width 50) (sprintf "%.2f")
  • Output │ │ 1961│70.32│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1962│70.22│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1963│69.74│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1964│69.57│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1965│69.50│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1966│69.38│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1967│69.29│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1968│69.21│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1969│68.77│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1970│68.61│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1971│60.01│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1972│59.53│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1973│59.44│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1974│59.51│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1975│59.56│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1976│59.60│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1977│59.50│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1978│59.80│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1979│59.87│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1980│59.71│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1981│59.67│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1982│59.62│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1983│58.69│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1984│58.63│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1985│58.12│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1986│57.94│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1987│57.84│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1988│57.25│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1989│57.29│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1990│57.26│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1991│54.59│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1992│54.33│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1993│54.10│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1994│53.39│■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1995│52.13│■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1996│52.19│■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1997│52.17│■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1998│52.65│■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 1999│53.72│■■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 2000│53.17│■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 2001│52.71│■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 2002│51.93│■■■■■■■■■■■■■■■■■■■■■■■■■■■■ 2003│50.68│■■■■■■■■■■■■■■■■■■■■■■■■■■■ 2004│50.60│■■■■■■■■■■■■■■■■■■■■■■■■■■■ 2005│50.10│■■■■■■■■■■■■■■■■■■■■■■■■■■■ 2006│48.29│■■■■■■■■■■■■■■■■■■■■■■■■■■ 2007│48.15│■■■■■■■■■■■■■■■■■■■■■■■■■■ 2008│49.15│■■■■■■■■■■■■■■■■■■■■■■■■■■ 2009│47.54│■■■■■■■■■■■■■■■■■■■■■■■■■ 2010│48.71│■■■■■■■■■■■■■■■■■■■■■■■■■■ 2011│47.10│■■■■■■■■■■■■■■■■■■■■■■■■■ 2012│46.68│■■■■■■■■■■■■■■■■■■■■■■■■■ 2013│46.34│■■■■■■■■■■■■■■■■■■■■■■■■■ 2014│44.75│■■■■■■■■■■■■■■■■■■■■■■■■ 2015│44.01│■■■■■■■■■■■■■■■■■■■■■■■ │ │
union case Width.FullWidth: Width


 Use the full width of the console
Multiple items
union case Width.Width: int -> Width


 The width of the chart including the printed title and value


--------------------
type Width =
  | FullWidth
  | Width of int
  member Value : int

Full name: Script.Width
Multiple items
val int : value:'T -> int (requires member op_Explicit)

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

--------------------
type int = int32

Full name: Microsoft.FSharp.Core.int

--------------------
type int<'Measure> = int

Full name: Microsoft.FSharp.Core.int<_>
val self : Width
member Width.Value : int

Full name: Script.Width.Value
namespace System
type Console =
  static member BackgroundColor : ConsoleColor with get, set
  static member Beep : unit -> unit + 1 overload
  static member BufferHeight : int with get, set
  static member BufferWidth : int with get, set
  static member CapsLock : bool
  static member Clear : unit -> unit
  static member CursorLeft : int with get, set
  static member CursorSize : int with get, set
  static member CursorTop : int with get, set
  static member CursorVisible : bool with get, set
  ...

Full name: System.Console
property System.Console.WindowWidth: int
val value : int
val drawBarChartWith : width:Width -> valueFormatter:('a -> string) -> xs:seq<string * 'a> -> unit (requires comparison and member op_Explicit)

Full name: Script.drawBarChartWith
val width : Width
val valueFormatter : ('a -> string) (requires comparison and member op_Explicit)
val xs : seq<string * 'a> (requires comparison and member op_Explicit)
Multiple items
val string : value:'T -> string

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

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

Full name: Microsoft.FSharp.Core.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<_>
module Seq

from Microsoft.FSharp.Collections
val cache : source:seq<'T> -> seq<'T>

Full name: Microsoft.FSharp.Collections.Seq.cache
val maxTitleWidth : int
val map : mapping:('T -> 'U) -> source:seq<'T> -> seq<'U>

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

Full name: Microsoft.FSharp.Core.Operators.fst
module String

from Microsoft.FSharp.Core
val length : str:string -> int

Full name: Microsoft.FSharp.Core.String.length
val max : source:seq<'T> -> 'T (requires comparison)

Full name: Microsoft.FSharp.Collections.Seq.max
val maxValue : 'a (requires comparison and member op_Explicit)
val snd : tuple:('T1 * 'T2) -> 'T2

Full name: Microsoft.FSharp.Core.Operators.snd
val maxValueWidth : int
val factor : float
Multiple items
val float : value:'T -> float (requires member op_Explicit)

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

--------------------
type float = System.Double

Full name: Microsoft.FSharp.Core.float

--------------------
type float<'Measure> = float

Full name: Microsoft.FSharp.Core.float<_>
property Width.Value: int
val emptyTitle : string
val replicate : count:int -> str:string -> string

Full name: Microsoft.FSharp.Core.String.replicate
val emptyValue : string
val printfn : format:Printf.TextWriterFormat<'T> -> 'T

Full name: Microsoft.FSharp.Core.ExtraTopLevelOperators.printfn
val title : string
val value : 'a (requires comparison and member op_Explicit)
val paddedTitle : string
val width : int
val value : string
val segments : string
val drawBarChart : xs:seq<string * 'a> -> unit (requires comparison and member op_Explicit)

Full name: Script.drawBarChart
Multiple items
namespace FSharp

--------------------
namespace Microsoft.FSharp
Multiple items
namespace FSharp.Data

--------------------
namespace Microsoft.FSharp.Data
val data : WorldBankData.ServiceTypes.WorldBankDataService

Full name: Script.data
type WorldBankData =
  static member GetDataContext : unit -> WorldBankDataService
  nested type ServiceTypes

Full name: FSharp.Data.WorldBankData


<summary>Typed representation of WorldBank data. See http://www.worldbank.org for terms and conditions.</summary>
WorldBankData.GetDataContext() : WorldBankData.ServiceTypes.WorldBankDataService
val idc : Runtime.WorldBank.Indicator

Full name: Script.idc
property WorldBankData.ServiceTypes.WorldBankDataService.Countries: WorldBankData.ServiceTypes.Countries
property WorldBankData.ServiceTypes.Countries.Italy: WorldBankData.ServiceTypes.Country


The data for country 'Italy'
property WorldBankData.ServiceTypes.Country.Indicators: WorldBankData.ServiceTypes.Indicators


<summary>The indicators for the country</summary>
val yearsWithValues : seq<int * float>

Full name: Script.yearsWithValues
val zip : source1:seq<'T1> -> source2:seq<'T2> -> seq<'T1 * 'T2>

Full name: Microsoft.FSharp.Collections.Seq.zip
property Runtime.WorldBank.Indicator.Years: System.Collections.Generic.ICollection<int>
property Runtime.WorldBank.Indicator.Values: System.Collections.Generic.ICollection<float>
val x : int
val y : float
val sprintf : format:Printf.StringFormat<'T> -> 'T

Full name: Microsoft.FSharp.Core.ExtraTopLevelOperators.sprintf

More information

Link:http://fssnip.net/7UB
Posted:15 days ago
Author:Tobias Burger
Tags: #console , #chart , #barchart