Thursday, 25 June 2015

Snippet: Searching web pages.

The idea's from Professional F# 2.0, Chapter 17 (by Ted Neward, Aaron C. Erickson, Talbott Crowell, Richard Minerich). Because there are 4 of them I'll call them the fgang of four, or FoF. When searching a dropdown list via a form, a web page form may return a value or nothing at all. F# handles nothing at all with None. Suppose our database data contained:

type VacationLocation =
    { Name: string; Pop: int; Density: int; Nightlife: int }
let destinations =
    [ { Name = "New York"; Pop = 9000000; Density = 27000; Nightlife = 9 }
      { Name = "Munich"; Pop = 1300000; Density = 4300; Nightlife = 7 }
      { Name = "Tokyo"; Pop = 13000000; Density = 15000; Nightlife = 3 }
      { Name = "Rome"; Pop = 2700000; Density = 5500; Nightlife = 5 } ]

Our web page filters user selections by city name, population, population density, and night life. A user will often ignore a selection. So each selection will be an option. A first iteration of F# can handle it likewise, using the identity function id:

let getVacationPipeline nightlifeMin sizeMin densityMax searchName =
    match nightlifeMin with
    | Some(n) -> List.filter (fun x -> x.Nightlife >= n)
    | None -> id
    >> match sizeMin with
       | Some(s) -> List.filter (fun x -> x.Pop / x.Density >= s)
       | None -> id
    >> match densityMax with
       | Some(d) -> List.filter (fun x -> x.Density <= d)
       | None -> id
    >> match searchName with
       | Some(sn) -> List.filter (fun x -> x.Name.Contains(sn))
       | None -> id

This function is applied to the data like so:

let applyVacationPipeline data filterPipeline =
    data
    |> filterPipeline
    |> List.map (fun x -> x.Name)

with filterPipeline a general function to be applied for the where clause. The last line is the select clause.

let myPipeline = getVacationPipeline (Some 5) (Some 200) (Some 8000) None
applyVacationPipeline destinations myPipeline

This match ... with ... some ... None -> id is repetitive, so we abstract it out as a getFilter function. It becomes:

let getVacationPipeline2 nightlifeMin sizeMin densityMax searchName =
    let getFilter filter some =
        match some with
        | Some(v) -> List.filter (filter v)
        | None -> id
    getFilter (fun nlMax x -> x.Nightlife >= nlMax) nightlifeMin
    >> getFilter (fun sMax x -> x.Pop / x.Density >= sMax) sizeMin
    >> getFilter (fun dMin x -> x.Density < dMin) densityMax
    >> getFilter (fun sName x -> x.Name.Contains(sName)) searchName

We can invoke it like so:

let myPipeline2 = getVacationPipeline2 (Some 5) (Some 200) (Some 8000) None
applyVacationPipeline destinations myPipeline2

The FoF is more detailed, beginning with an imperative version (??). I suspect every C# programmer gave up such imperative code long ago for Linq.

F# automatically handles missing data. Because we can compose our queries, each may be simply tested too.

Monday, 5 January 2015

Russian propaganda (cyber-warfare?) example on twitter

Russia has been accused of funding and propagandising anti-fracking campaigns in the West1, 2. Natural gas is a famous Russian export but many energy exports (gas, oil, coal, nuclear power) are important to the Russian economy. The recent fall in the price of oil even precipitated an economic crisis there. Preventing fracking in Europe is a good way to keep natural gas prices high. They've already had a lot of success in that area.

Given they have the 'resources' in place, it seems obvious to turn against nuclear power too. One such example is their recent twitter campaign, using the hashtags #FukushimaAgain #Chernobyl2015. It's already been noted that the 'accident' to the reactor in the Ukraine was an incident not an accident4. Russian media sources are systematically misreporting the events in Ukraine, and at Ukraine nuclear reactors too5.

These are just the first 10 accounts I looked at tweeting those hashtags. I've no idea how many more there are of them.

These accounts don't, at first, look fake. A detailed investigation shows otherwise: they are hijacked or fake:

  • most of the accounts only began tweeting within the last few weeks
  • the accounts have a few hundred tweets each, often made very recently
  • they rarely, if ever, tweet to anyone else
  • they don't engage anyone in a conversation
  • many of the innocent looking tweets are garbage:
    • common quotes from famous people e.g.:
    • 'witty', or 'pseudo-intellectual' observations. e.g.:
  • here's an example of a tweet that belongs to a conversation. A message to a friend. Who might that be?:
  • tweets are often made with very short time intervals between them - indicating the person has nothing better to do than, essentially, repeat the same tweet. More like it's a bot using random time intervals.
  • tweets are likely to be gender neutral, geographically neutral. The bot doesn't know whether it's pretending to be male/female or whatever. The more specific the tweet, the more trouble a programmer must endure to fake it.

For more on fake twitter accounts see: 6

References

  1. NATO Chief: Putin Behind Anti-Fracking Campaigns
  2. Russia’s Quiet War Against European Fracking
  3. Russia says 'spies' work in foreign NGOs
  4. Reporting an Incident as an Accident
  5. Ukraine Nuclear Plants - Resources and Information
  6. 11 Easy Ways To Spot a Fake Twitter Account

Thursday, 26 June 2014

Today I discovered Elm

Web pages are broke. They always were, from the inception of html, to all the fixes: css, JavaScript, DHTML, Ajax. Now we have an explosion of fixes: sass, lass, Jade, JRX, an explosion of MVM and, even MVVM frameworks. An army of languages to write JavaScript with. Are we doomed to ever more complexity; cludge piled upon fix glued together by compromise?

Is there a light at the end of the tunnel? Today I discovered Elm. Video presentations:

Some links

Academic (papers)

And a Haskell page to remember.

F# computation expressions

Wednesday, 25 June 2014