Bath Clean Air Zone

BANES is to be congratulated for creating a plan to tackle the air pollution that is generated by transport in Bath. Unfortunately the plan has several flaws:
  • It doesn't consider pollution from brake and tyre dust.
  • It considers pollution per vehicle rather than pollution per person.
  • It doesn't help tackle congestion.
  • It is biased towards wealthy car users.
 Cars generate more pollution per person than buses. Cars also impede the progress of buses within the city, making buses expensive, slow and unreliable. The key therefore is to reduce the number of cars in the city, thus improving air quality and making it easier for people to travel in the city using buses. How can this be achieved?

The solution is to turn all parking in the city into residents' parking zones, where each resident has a reserved space in their local zone, but all other spaces have to be purchased at a higher price. Thus residents' parking zones reduce the number of cars on the road, making it cheaper and easier to use buses, and reducing air pollution from exhaust, brakes and tyres.

Some may argue that even if buses aren't impeded by cars, the fares won't be reduced and the company will pocket the extra profit. If this happens, then BANES should use a Quality Contract Scheme to punish anti-competitive behaviour by bus operators.

Bus operators have adopted electronic ticketing in BANES where you activate your ticket on the phone just before boarding, and show the screen to the driver as you walk past. This is a great step forward, but the problem is that you have to buy a separate batch of tickets for each bus operator. BANES need to step in here and require that the same tickets work for any bus company.

With people travelling by bus rather than car, an immediate improvement is made to transport in Bath. However, we shouldn't stop there! Trams are superior to buses in that they pollute less, are cheaper to operate, have a higher capacity and are more pleasant to travel in. With the money generated from the parking zones, BANES should begin to build a Bath tram network.


Increasingly concerned about Facebook, Google etc

For some time I've been concerned about Google, Facebook etc. I'm writing this to try and pin down what my concerns are and what (if anything) I should do about it. So here are some thoughts in no particular order (a 'brain dump' in the vernacular):


It seems that with Facebook there's a network effect, where the value of being part of a network increases with its size. So with Facebook, if 'everybody is on Facebook' then that's the one I'll join because I'll be able to communicate with everyone else. Conversely, leaving Facebook and trying to persuade people to use Signal is difficult. I've tried and people just don't want to move

Open Source

This seems to be part of the solution. I'd call it a necessary, but not sufficient condition. With proprietary software you can't see what the software is doing, which is troubling to me. With open source software, people with the skill to read the code can raise the alarm if it's doing anything underhand.

Internet Freedom

Perhaps part of what I'm concerned about could be called 'freedom on the internet'. Freedom from billionaires paying money to internet monopolies to influence me in an underhand way.

Walled Gardens

Walled gardens are part of the problem. Avoid them!


I suppose it's not so much advertising, it's the diabolically clever targeting of it. For example, DuckDuckGo has advertising, but it doesn't track you, and so there's none of that collection of personal data which is then used to manipulate you. Perhaps I'm saying that anything that allows micro-targeting is bad. So that would include any necessary steps (collecting personal data, organizing it in order to target people, and the actual adverts itself).

So those are, briefly, some of the problems. Here are some tentative solutions:

Open Source on mobile phone

I already use an open source operating system on my laptop, but my mobile phone runs stock Android. Really I should follow the steps that the FSFE gives to Liberate Your Device.

Move away from Google

This is difficult. One thing I can do is move this blog and my website to be a simple static site, hosted without charge. The other thing is to review my various applications hosted on Google AppEngine and see what can be done about those.


IPFS is an alternative to the web, but still uses the internet. I should start to get to know it, and perhaps write an app. This won't solve things immediately, but it (or something like it) is needed.

I think that's enough for now. I'll try and make a bit of progress and then come back and see what more I can do.


How many flips of a coin before I get 7 heads in a row?

Bill asked, 'On average, how many flips of a coin do I have to do to get 7 heads in a row?'. I thought this would be really easy, but I had to think about it for ages. I think it means, how many flips to get 50% probability of getting 7 heads in a row. On Maths StackExchange there was an answer that I didn't fully understand, but it said to do 1 - (probability of not getting 7 in a row). It also said to think about 'atoms' which for 7 heads are:


The idea is that the number of ways of not getting 7 heads in a row if you flip the coin 40 times, is the number of ways of arranging the atoms so that the total length is 41. I tried it out with smaller numbers first, so I thought about the chances of getting 2 heads in a row for 2 coin tosses. So in this case the atoms are:


and the ways of arranging them in a total length of 3 are:


So there are 3 of them, and the total number of combinations are 2^2 = 4, giving a probability of not getting two heads in a row of 3/4, and so the probability of getting two heads in a row is 1 - 3/4 = 1/4. Which we know is correct. So the problem now is, how do we work out the number of ways of arranging the atoms for 2 heads in an arbitrary length?

The picture below shows how I imagine it:

Starting at zero, the single arrows mean an atom of length 1 (ie. a tail), and a double arrow means an atom of length 2 (ie. a head followed by a tail). The number of ways of getting to a certain length, is equal to the number of different paths to get to the number on the graph in the picture (that's what the number in brackets is). So for example, there are two ways to get to length 2, one way is to go from zero directly, and the other way is go via 1. Looking at the number of ways as the path length increases you get a fibonacci sequence:

0, 1, 1, 2, 3, 5, 8, 13, ...

So if there are n coin tosses the probability of getting two heads in a row is:

1 - fib(n + 1) / 2^n

So there we have it for 2 heads in a row, but what about 3? I drew another diagram, but with 3 arrows coming from each length rather than 2, and the number of ways of not getting 3 heads in a row was a tribonacci sequence. The next term of the fibonacci sequence if found by adding up the two previous terms, but the next term in the tribonacci sequence is found by adding up the three previous terms. So it goes:

0, 0, 1, 1, 2, 4, 7, 13, 24, 44, 81, ...

Say the nth term of a kth order fibonacci sequence is fib(k, n), then the probability of getting k heads in n flips is:

1 - fib(k, n) / 2^n

There's probably some fancy way of working this out, but I wrote a Python 3.6 programme to do it:

prob = 0

while prob < 0.5:
    first_key, first_val = sorted(stream.items())[0]
    for v in range(NUM_IN_A_ROW):
        stream[first_key + v + 1] += first_val
    prob = 1 - stream[first_key + 1] / 2 ** first_key
        "After " + str(first_key) + " flips the probability of getting " +
        str(NUM_IN_A_ROW) + " in a row is " + str(prob))
    del stream[first_key] 

Running this gives: After 178 flips the probability of getting 7 in a row is 0.5014494277755364. So my answer is 178!

Any corrections and comments welcome :-)

Update 2018-04-08

Having thought about the maths again, I think the Python can be written in a better way, and the deque data structure is well suited to finding n-order fibonacci sequences. So here's my second attempt, and reassuringly it comes out with the same answer.

from collections import deque
from itertools import count

fibs = deque([1], NUM_IN_A_ROW)
tot = 1

for n in count():
    fib = sum(fibs)
    prob = 1 - fib / tot
        f"After {n} flips the probability of getting {NUM_IN_A_ROW} in a row "
        f"is {prob}")
    if prob >= 0.5:
    tot *= 2