Uncommon Descent Serving The Intelligent Design Community

The Original WEASEL(s)

Share
Facebook
Twitter
LinkedIn
Flipboard
Print
Email

On August 26th last month, Denyse O’Leary posted a contest here at UD asking for the original WEASEL program(s) that Richard Dawkins was using back in the late 1980s to show how Darwinian evolution works. Although Denyse’s post generated 377 comments (thus far), none of the entries could reasonably be thought to be Dawkins’s originals.

It seems that Dawkins used two programs, one in his book THE BLIND WATCHMAKER, and one for a video that he did for the BBC (here’s the video-run of the program; fast forward to 6:15). After much beating the bushes, we finally heard from someone named “Oxfordensis,” who provided the two PASCAL programs below, which we refer to as WEASEL1 (corresponding to Dawkins’s book) and WEASEL2 (corresponding to Dawkins’s BBC video). These are by far the best candidates we have received to date.

Unless Richard Dawkins and his associates can show conclusively that these are not the originals (either by providing originals in their possession that differ, or by demonstrating that these programs in some way fail to perform as required), we shall regard the contest as closed, offer Oxfordensis his/her prize, and henceforward treat the programs below as the originals.

For WEASEL1 and WEASEL2 click here:

WEASEL1:

Program Weasel;

Type

Text=String[28];

(* Define Parameters *)

Const

Alphabet:Text=’ABCDEFGHIJKLMNOPQRSTUVWXYZ ‘;

Target:Text=’METHINKS IT IS LIKE A WEASEL’;

Copies:Integer=100;

Function RandChar:Char;

(* Pick a character at random from the alphabet string *)

Begin

RandChar:=Alphabet[Random(27)+1];

End;

Function SameLetters(New:Text; Current:Text):Integer;

(* Count the number of letters that are the same *)

Var

I:Integer;

L:Integer;

Begin

L:=0;

I:=0;

While I< =Length(New) do Begin If New[I]=Current[I] Then L:=L+1; I:=I+1; End; SameLetters:=L; End; Var Parent:Text; Child:Text; Best_Child:Text; I:Integer; Best:Integer; Generation:Integer; Begin Randomize; (* Initialize the Random Number Generator *) (* Create a Random Text String *) Parent:=''; For I:=1 to Length(Target) do Begin Parent:=Concat(Parent, RandChar) End; Writeln(Parent); (* Do the Generations *) Generation:=1; While SameLetters(Target, Parent) <> Length(Target)+1 do

Begin

(* Make Copies *)

Best:=0;

For I:=1 to Copies do

Begin

(* Each Copy Gets a Mutation *)

Child:=Parent;

Child[Random(Length(Child))+1]:=RandChar;

(* Is This the Best We’ve Found So Far? *)

If SameLetters(Child, Target) > Best Then

Begin

Best_Child:=Child;

Best:=SameLetters(Child, Target);

End;

End;

Parent:=Best_Child;

(* Inform the User of any Progress *)

Writeln(Generation, ‘ ‘, Parent);

Generation:=Generation+1;

End;

End.

WEASEL2:

PROGRAM WEASEL;
USES
CRT;

(* RETURN A RANDOM LETTER *)
FUNCTION RANDOMLETTER : CHAR;
VAR
NUMBER : INTEGER;
BEGIN
NUMBER := RANDOM(27);
IF NUMBER = 0 THEN
RANDOMLETTER := ‘ ‘
ELSE
RANDOMLETTER := CHR( ORD(‘A’) + NUMBER – 1 );
END;

(* MEASURE HOW SIMILAR TWO STRINGS ARE *)
FUNCTION SIMILARITY(A : STRING; B : STRING) : INTEGER;
VAR
IDX : INTEGER;
SIMCOUNT : INTEGER;
BEGIN
SIMCOUNT := 0;

FOR IDX := 0 TO LENGTH(A) DO
BEGIN
IF A[IDX] = B[IDX] THEN
SIMCOUNT := SIMCOUNT + 1;
END;
SIMILARITY := SIMCOUNT;
END;

FUNCTION RANDOMSTRING(LEN : INTEGER) : STRING;
VAR
I : INTEGER;
RT : STRING;
BEGIN
RT := ”;
FOR I := 1 TO LEN DO
BEGIN
RT := RT + RANDOMLETTER;
END;
RANDOMSTRING := RT;
END;

VAR
X : INTEGER;
TARGET : STRING;
CURRENT : STRING;
OFFSPRING : STRING;
TRIES : LONGINT;
FOUND_AT : INTEGER;
BEGIN
RANDOMIZE;

CLRSCR;

WRITELN(‘Type target phrase in capital letters’);
READLN(TARGET);
(* PUT SOME STRING ON THE SCREEN *)
TEXTCOLOR(GREEN);
GOTOXY(1, 6);
WRITELN(‘Target’);

GOTOXY(10, 6);
WRITELN(TARGET);

TEXTCOLOR(BLUE);

GOTOXY(1,13);
WRITELN(‘Darwin’);

TEXTCOLOR(BLUE);
GOTOXY(1,19);
WRITELN(‘Random’);

TEXTCOLOR(WHITE);
GOTOXY(1, 25);

WRITE(‘Try number’);

(* PICK A RANDOM STRING TO START DARWIN SEARCH *)
CURRENT := RANDOMSTRING(LENGTH(TARGET));

(* RUN THROUGH MANY TRIES *)
FOUND_AT := 0;
FOR TRIES := 1 TO 100000 DO
BEGIN

(* Darwin *)
OFFSPRING := CURRENT;
OFFSPRING[ 1 + RANDOM(LENGTH(OFFSPRING)) ] := RANDOMLETTER;

GOTOXY(10,13);
WRITELN(OFFSPRING, ‘ ‘);

IF( SIMILARITY(OFFSPRING, TARGET) >= SIMILARITY(CURRENT, TARGET) ) THEN
CURRENT := OFFSPRING;

IF( (SIMILARITY(CURRENT, TARGET) = LENGTH(TARGET)) AND (FOUND_AT = 0) ) THEN
BEGIN
(* TELL THE USER WHAT WE FOUND *)
FOUND_AT := TRIES;
GOTOXY(1, 15);
TEXTCOLOR(BLUE);
WRITELN(‘Darwin’);
TEXTCOLOR(WHITE);
GOTOXY(9, 15);
WRITELN(‘reached target after’);
GOTOXY(37, 15);
TEXTCOLOR(BLUE);
WRITELN(FOUND_AT);
WRITE(‘tries’);
TEXTCOLOR(WHITE);

GOTOXY(1, 21);
TEXTCOLOR(BLUE);
WRITE(‘Random’);
TEXTCOLOR(WHITE);
WRITELN(‘ would need more than ‘);
TEXTCOLOR(BLUE);
WRITELN(‘1000000000000000000000000000000000000000’);
TEXTCOLOR(WHITE);
WRITE(‘tries’);
END;

(* Random *)
GOTOXY(10, 19);
WRITELN(RANDOMSTRING(LENGTH(TARGET)), ‘ ‘);

GOTOXY(27,25);
WRITE(TRIES, ‘ ‘);
END;

GOTOXY(1, 20);
End.

Comments
"I can’t imagine why Dawkins would limit mutation so it can only EVER apply to one letter – it doesn’t seem very biological." An argument from lack of imagination? Interesting... Granted its not very "biological"; however, it is simpler to code. This version uses one line of code to change a random letter. The most straightforward method to implement the multiple-mutation scheme would involve a loop over all the characters. Certainly not impossible or even difficult for an experience coder. Nevertheless, it would be simpler not to. I don't think Dawkins was attempting to produce an accurate model of biology here. All he was attempting to demonstrate was the power of cumulative selection over non-cumulative selection. A more accurate mutation scheme really wouldn't have been useful.AndrewFreeman
September 19, 2009
September
09
Sep
19
19
2009
09:50 PM
9
09
50
PM
PDT
I coded a quick and dirty version of both the OP algorithm and a similar version that uses the proposed mutation rate per letter scheme. One-mutation-per-child with 100 children (as per the OP) gives me: 40-60 generations which seems consistent with the examples in the text. 4% mutation rate with 50 children as per DieB: 90-120 generations. 5% mutation rate with 50 children as per DieB: 120-150 generations. 4% mutation rate with 10 children as per DieB: 600-2000 generations 4% mutation rate with 200 children per generation: 40-60 generations. The given algorithm appears to produce similar convergence times whereas it takes a larger population then has been previously proposed to get the same range with the multiple mutation scheme.AndrewFreeman
September 19, 2009
September
09
Sep
19
19
2009
09:45 PM
9
09
45
PM
PDT
Under the OP's algorithm, we'd expect to get one letter changed per generation. On the other hand, if multiple mutations are possible we'd expect to have at least some generations where multiple letters were fixed. The first run showing every ten generations, and the number of letters fixed in that time: (assuming that I've copied the strings over correctly. I'm using a python script to help make sure I'm counting the changes correctly) WDLDMNLT DTJBKWIRZREZLMQCO P : ancestor WDLDMNLT DTJBKWIRZREZLMQCO P : 9 MDLDMNLS ITJISWHRZREZ MECS P : 10 MELDINLS IT ISWPRKE Z WECSEL : 6 METHINGS IT ISWLIKE B WECSEL : 4 The second run: Y YVMQKZPFJXWVHGLAWFVCHQYOPY : ancestor Y YVMQKZPFJXWVHGLAWFVCHQYOPY : 9 Y YVMQKSPFTXWSHLIKEFV HQYSPY : 10 YETHINKSPITXISHLIKEFA WQYSEY : 7 METHINKS IT ISSLIKE A WEFSEY : 3 METHINKS IT ISBLIKE A WEASES : 2 METHINKS IT ISJLIKE A WEASEO : 3 Both runs peak at 10 letters fixed in ten generations which would seem to lend support to the idea of having one mutation per child.AndrewFreeman
September 19, 2009
September
09
Sep
19
19
2009
09:34 PM
9
09
34
PM
PDT
Ah, I hadn't noticed the similarity between the non-cumulative selection and the starting points for the cumulative selection. There seems to be a number of typos in the strings. The first generation of the first run is, as mentioned, too short. The first generation of the second run is too long. It seems to have an extra X. So it is not too much a suggest an additional typo. For the string to have had a D in that location, switching to a D, and back to a T seems rather unlikely.AndrewFreeman
September 19, 2009
September
09
Sep
19
19
2009
09:08 PM
9
09
08
PM
PDT
AndrewFreeman:
The two generations in question: 1 WDLMNLT DTJBKWIRZREZLMQCO P 2 WDLTMNLT DTJBSWIRZREZLMQCO P However, somethings not quite right since the first one is shorter then it should be… If we assume it is a typographical error, where T is missing from generation 1, only one difference remains.
If you look at the top of page 47, you'll see the first generation of Dawkins' non-cumulative selection run. The sequence is the same as the first generation of the cumulative selection run, with a 'D' in the position of the missing letter. It seems that the most likely explanation is that Dawkins used the same random seed in both runs, but the 'D' was accidentally omitted when the original sequence of the cumulative run was transcribed. Of course, it may be that the 'T' at the top of page 48 should be a 'D' -- another typo. This would be supported by the fact that there is a 'D' in that position after 10 and 20 generations. That scenario seems very plausible to me, and in that case, the algorithms in the OP could indeed be accurate reflections of the algorithm in TBW.R0b
September 19, 2009
September
09
Sep
19
19
2009
08:01 PM
8
08
01
PM
PDT
For Cannuckian Yankee at 14: No, unfortunately. The raggedy copy wouldn't help in this situation. I have a bunch of them going to local libraries now. The general idea of the contest is that I must provide mint copies from the publisher to the winner. Some people even want me to sign them, when I had nothing to do with the book ... I will solve this problem by acquiring winner certificates at the local office supply store shortly. Anyway, if you know any publishers of books of interest, pester them to be generous to us.O'Leary
September 19, 2009
September
09
Sep
19
19
2009
06:02 PM
6
06
02
PM
PDT
OT Denyse, "...and solicit new prizes from publishers hit by the recession." and "...so if you have a brilliant idea, get it in soon." I have an extra copy (a little raggedy) of Darwin's Black Box. Will that help? :)CannuckianYankee
September 19, 2009
September
09
Sep
19
19
2009
05:15 PM
5
05
15
PM
PDT
To DiEB at 6: "As Both comments and pings are currently closed at O’Leary’s thread, there won’t be any additional comments over there. That’s a pity" Well, it would be a pity if you didn't need to declare a winner from nearly 400 comments, and still judge other contests and put up more contests, and solicit new prizes from publishers hit by the recession. I think our mod closes comments after four weeks, so if you have a brilliant idea, get it in soon.O'Leary
September 19, 2009
September
09
Sep
19
19
2009
04:41 PM
4
04
41
PM
PDT
Dr Dembski, Of these two original programs, which uses explicit latching ('86) and which uses quasi-latching ('87)?steve_h
September 19, 2009
September
09
Sep
19
19
2009
04:06 PM
4
04
06
PM
PDT
BTW, I did some math for the latching behavior of this program: have a look here.DiEb
September 19, 2009
September
09
Sep
19
19
2009
03:48 PM
3
03
48
PM
PDT
As a professional programmer with way over a million lines of Pacal code written, I can say unequivocally that computationally this program is trivial. I recently spent a few hours writing a grandchild-generator program that simulated the distribution of grandparental chromosomes, and it was longer and more involved than this. By the way, the program showed that if you wanted your chromosomes to get much further than your grandchildren, you needed to have at least four children, all making grandchildren. It makes you understand grandparentally-arranged marriages between cousins, which keeps those grandparental chromosomes around much longer, but which was recently shown to have no elevated risk of inbreeding. Nevertheless, good luck pulling that off here.Interstelar Bill
September 19, 2009
September
09
Sep
19
19
2009
03:04 PM
3
03
04
PM
PDT
Even this algorithm is not necessarily latching: it could be that all members of a generations have a change to the worse - that's especially probable if most letters are correct already. Only kairofocus's implicit latching is prevented...DiEb
September 19, 2009
September
09
Sep
19
19
2009
02:22 PM
2
02
22
PM
PDT
Wait, wait, wait. In his book Dawkins CLEARLY reproduced only some of his program generated output whereas in the TV program more could be seen. AND . . . you're trusting this person "Oxfordensis"? It was just a program to demonstrate that one aspect of evolution was reasonable AND . . . . "Oxfordensis"? Dr Dembski . . . you've got to provide us with more evidence than this surely! At least tell us why YOU think these programs are believable. They don't even look like they were written by the same person!! Have you compiled these to see if they come close to producing the output observed? :-) Don't blow this guys . . . PZ will be all over you if you do!!ellazimm
September 19, 2009
September
09
Sep
19
19
2009
02:20 PM
2
02
20
PM
PDT
Ah, I think I see whats going on, very clever. With a low mutation rate on the real WEASEL you can get an average of one mutation per offspring, which will produce the result that AndrewFreeman posted. Fixing the 'mutation rate' so it can only ever be one letter per offspring is very different that giving each letter a low probability of mutating. Giving each letter a random chance of mutating, and selecting the right mutation rate may average out at one letter change per offspring but, like any average measure, the actual results can vary from moment to moment - you can have an offspring with three mutated letters, it is just more unlikely that an offspring with one or none. WEASEL 1 above doesn't allow this. Dawkins output only gives the first two consecutive parents followed by every tenth parent, which should average out at one mutation per offspring, so there is not enough info in his results to tell the difference. Where the WEASEL1 above is really clever is that, by fixing the mutation to one letter per offspring, you create a latching mechanism because a reversion of a correct letter can never be balanced by another correct letter being found. In this way you always preserve offspring that don't show reversions, Unlike the real WEASEL where this is a probabilistic outcome dependent on the choice of mutation rate and pop size. I can't imagine why Dawkins would limit mutation so it can only EVER apply to one letter - it doesn't seem very biological.BillB
September 19, 2009
September
09
Sep
19
19
2009
02:16 PM
2
02
16
PM
PDT
3. IMO Dawkins used the same algorithm in his book and the video, he just changed the parameters: in his book, the population size seems to be fifty, while for the video, it seems to be ten - and both times, a mutation probability of 4%-5% seemed to be used.DiEb
September 19, 2009
September
09
Sep
19
19
2009
01:45 PM
1
01
45
PM
PDT
1. As Both comments and pings are currently closed at O'Leary's thread, there won't be any additional comments over there. That's a pity. 2. In this 377 comments, at least the consensus emerged that the algorithm in the paper of Dembski and Marks (described by kairosfocus as an unrealistic illustration) is not the algorithm of Dawkins's book.DiEb
September 19, 2009
September
09
Sep
19
19
2009
01:42 PM
1
01
42
PM
PDT
R0b:
Regardless, it looks like we’ve finally gotten past the idea that Dawkins’ algorithm is a partitioned search.
It just acts like one.Joseph
September 19, 2009
September
09
Sep
19
19
2009
01:28 PM
1
01
28
PM
PDT
The two generations in question: 1 WDLMNLT DTJBKWIRZREZLMQCO P 2 WDLTMNLT DTJBSWIRZREZLMQCO P However, somethings not quite right since the first one is shorter then it should be... If we assume it is a typographical error, where T is missing from generation 1, only one difference remains.AndrewFreeman
September 19, 2009
September
09
Sep
19
19
2009
01:16 PM
1
01
16
PM
PDT
BillB is right. Both of the above programs mutate exactly one letter per offspring, but the results reported at the top of page 48 in TBW show two changes occurring between the first and second generations. Regardless, it looks like we've finally gotten past the idea that Dawkins' algorithm is a partitioned search.R0b
September 19, 2009
September
09
Sep
19
19
2009
12:33 PM
12
12
33
PM
PDT
Although I'm still brushing up on my PASCAL it looks like WEASAEL 1 is wrong - It only mutates one letter for each offspring, whereas each letter for each offspring should have a probability of mutating. I'll try and feed it into a compiler if I can resurrect one, but I really can't see this ever reproducing the results in TBW.BillB
September 19, 2009
September
09
Sep
19
19
2009
12:12 PM
12
12
12
PM
PDT
Well, I can manage a contest but don't know code. So naturally, this development pleases me. If we got 377 comments for Contest 10, I really must acquire more prizes, which I am now trying to do. I will judge Contest 9 next week, and am delighted to think I would be no use with Contest 10, as that gives me time to post more contests and fish for more prizes. I don't think the Contest 10 question will ever really be solved without the absolute real genuine original code. But if Oxfordensis is entitled to the prize, that individual must e-mail me a valid postal address at oleary@sympatico.caO'Leary
September 19, 2009
September
09
Sep
19
19
2009
09:37 AM
9
09
37
AM
PDT
1 3 4 5

Leave a Reply