source: branches/profile/GDE/PHYLIP/contml.c

Last change on this file was 2175, checked in by westram, 20 years ago

upgrade to PHYLIP 3.6

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 32.3 KB
Line 
1#include "phylip.h"
2#include "cont.h"
3
4/* version 3.6. (c) Copyright 1993-2001 by the University of Washington.
5   Written by Joseph Felsenstein, Akiko Fuseki, Sean Lamont, and Andrew Keeffe.
6   Permission is granted to copy and use this program provided no fee is
7   charged for it and provided that this copyright notice is not removed. */
8
9
10#define epsilon1        0.000001   /* small number */
11#define epsilon2        0.02   /* not such a small number */
12
13#define smoothings      4   /* number of passes through smoothing algorithm */
14#define maxtrees        10   /* maximum number of user trees in KHT test */
15
16#define over            60
17
18
19#ifndef OLDC
20/* function prototypes */
21void   getoptions(void);
22void   allocrest(void);
23void   doinit(void);
24void   getalleles(void);
25void   inputdata(void);
26void   getinput(void);
27void   sumlikely(node *, node *, double *);
28double evaluate(tree *);
29double distance(node *, node *);
30void   makedists(node *);
31
32void   makebigv(node *, boolean *);
33void   correctv(node *);
34void   littlev(node *);
35void   nuview(node *);
36void   update(node *);
37void   smooth(node *);
38void   insert_(node *, node *);
39void   copynode(node *, node *);
40void   copy_(tree *, tree *);
41void   inittip(long, tree *);
42
43void   buildnewtip(long, tree *, long);
44void   buildsimpletree(tree *);
45void   addtraverse(node *, node *, boolean);
46void   re_move(node **, node **);
47void   rearrange(node *);
48void   coordinates(node *, double, long *, double *);
49void   drawline(long, double);
50void   printree(void);
51void   treeout(node *);
52void   describe(node *, double, double);
53
54void   summarize(void);
55void   nodeinit(node *);
56void   initrav(node *);
57void   treevaluate(void);
58void   maketree(void);
59/* function prototypes */
60#endif
61
62
63Char infilename[FNMLNGTH], outfilename[FNMLNGTH], intreename[FNMLNGTH], outtreename[FNMLNGTH];
64long nonodes2, loci, totalleles, df, outgrno, col, datasets, ith,
65        njumble, jumb=0;
66long inseed;
67long *alleles, *locus, *weight;
68phenotype3 *x;
69boolean all, contchars, global, jumble, lengths, outgropt, trout,
70               usertree, printdata, progress, treeprint, mulsets, firstset;
71longer seed;
72long *enterorder;
73tree curtree, priortree, bestree, bestree2;
74long nextsp,numtrees,which,maxwhich; /* From maketree, propogated to global */
75boolean succeeded;
76double maxlogl;
77double l0gl[maxtrees];
78double *l0gf[maxtrees];
79Char ch;
80char *progname;
81double trweight;   /* added to make treeread happy */
82boolean goteof;
83boolean haslengths;   /* end of ones added to make treeread happy */
84
85
86void getoptions()
87{
88  /* interactively set options */
89  long inseed0, loopcount;
90  Char ch;
91  boolean done;
92
93  fprintf(outfile, "\nContinuous character Maximum Likelihood");
94  fprintf(outfile, " method version %s\n\n",VERSION);
95  putchar('\n');
96  global = false;
97  jumble = false;
98  njumble = 1;
99  lengths = false;
100  outgrno = 1;
101  outgropt = false;
102  all = false;
103  contchars = false;
104  trout = true;
105  usertree = false;
106  printdata = false;
107  progress = true;
108  treeprint = true;
109  loopcount = 0;
110  do {
111    cleerhome();
112    printf("\nContinuous character Maximum Likelihood");
113    printf(" method version %s\n\n",VERSION);
114    printf("Settings for this run:\n");
115    printf("  U                       Search for best tree?  %s\n",
116           (usertree ? "No, use user trees in input" : "Yes"));
117    if (usertree) {
118      printf("  L                Use lengths from user trees?%s\n",
119             (lengths ? "  Yes" : "  No"));
120    }
121    printf("  C  Gene frequencies or continuous characters?  %s\n",
122           (contchars ? "Continuous characters" : "Gene frequencies"));
123    if (!contchars)
124      printf("  A   Input file has all alleles at each locus?  %s\n",
125             (all ? "Yes" : "No, one allele missing at each"));
126    printf("  O                              Outgroup root?  %s %ld\n",
127           (outgropt ? "Yes, at species number" :
128                       "No, use as outgroup species"),outgrno);
129    if (!usertree) {
130      printf("  G                      Global rearrangements?  %s\n",
131             (global ? "Yes" : "No"));
132      printf("  J           Randomize input order of species?");
133      if (jumble)
134        printf("  Yes (seed=%8ld,%3ld times)\n", inseed0, njumble);
135      else
136        printf("  No. Use input order\n");
137    }
138    printf("  M                 Analyze multiple data sets?");
139    if (mulsets)
140      printf("  Yes, %2ld sets\n", datasets);
141    else
142      printf("  No\n");
143    printf("  0         Terminal type (IBM PC, ANSI, none)?  %s\n",
144           ibmpc ? "IBM PC" : ansi  ? "ANSI" : "(none)");
145    printf("  1          Print out the data at start of run  %s\n",
146           (printdata ? "Yes" : "No"));
147    printf("  2        Print indications of progress of run  %s\n",
148           (progress ? "Yes" : "No"));
149    printf("  3                              Print out tree  %s\n",
150           (treeprint ? "Yes" : "No"));
151    printf("  4             Write out trees onto tree file?  %s\n",
152           (trout ? "Yes" : "No"));
153    printf("\n  Y to accept these or type the letter for one to change\n");
154#ifdef WIN32
155    phyFillScreenColor();
156#endif
157    scanf("%c%*[^\n]", &ch);
158    getchar();
159    uppercase(&ch);
160    done = (ch == 'Y');
161    if (!done) {
162      if (strchr("JLOUGACM12340",ch) != NULL){
163
164        switch (ch) {
165
166        case 'A':
167          if (!contchars)
168            all = !all;
169          break;
170
171        case 'C':
172          contchars = !contchars;
173          break;
174
175        case 'G':
176          global = !global;
177          break;
178
179        case 'J':
180          jumble = !jumble;
181          if (jumble)
182            initjumble(&inseed, &inseed0, seed, &njumble);
183          else njumble = 1;
184          break;
185
186         case 'L':
187           lengths = !lengths;
188           break;
189
190        case 'O':
191          outgropt = !outgropt;
192          if (outgropt)
193            initoutgroup(&outgrno, spp);
194          break;
195
196        case 'U':
197          usertree = !usertree;
198          break;
199
200        case 'M':
201          mulsets = !mulsets;
202          if (mulsets)
203            initdatasets(&datasets);
204          break;
205
206        case '0':
207          initterminal(&ibmpc, &ansi);
208          break;
209
210        case '1':
211          printdata = !printdata;
212          break;
213
214        case '2':
215          progress = !progress;
216          break;
217
218        case '3':
219          treeprint = !treeprint;
220          break;
221
222        case '4':
223          trout = !trout;
224          break;
225        }
226      } else
227        printf("Not a possible option!\n");
228    }
229    countup(&loopcount, 100);
230  } while (!done);
231}  /* getoptions */
232
233
234void allocrest()
235{
236  alleles = (long *)Malloc(loci*sizeof(long));
237  if (contchars)
238    locus = (long *)Malloc(loci*sizeof(long));
239  x = (phenotype3 *)Malloc(spp*sizeof(phenotype3));
240  nayme = (naym *)Malloc(spp*sizeof(naym));
241  enterorder = (long *)Malloc(spp*sizeof(long));
242}  /* allocrest */
243
244
245void doinit()
246{
247  /* initializes variables */
248
249  inputnumbers(&spp, &loci, &nonodes2, 2);
250  getoptions();
251  if (printdata)
252    fprintf(outfile, "\n%4ld Populations, %4ld Loci\n", spp, loci);
253  alloctree(&curtree.nodep, nonodes2);
254  if (!usertree) {
255    alloctree(&bestree.nodep, nonodes2);
256    alloctree(&priortree.nodep, nonodes2);
257    if (njumble > 1) {
258      alloctree(&bestree2.nodep, nonodes2);
259    }
260  }
261  allocrest();
262}  /* doinit */
263
264
265void getalleles()
266{
267  /* set up number of alleles at loci */
268  long i, j;
269
270  if (!firstset)
271    samenumsp(&loci, ith);
272  if (contchars ) {
273    totalleles = loci;
274    for (i = 1; i <= loci; i++) {
275      locus[i - 1] = i;
276      alleles[i - 1] = 2;
277    }
278    df = loci;
279  } else {
280    totalleles = 0;
281    scan_eoln(infile);
282    if (printdata) {
283      fprintf(outfile, "\nNumbers of alleles at the loci:\n");
284      fprintf(outfile, "------- -- ------- -- --- -----\n\n");
285    }
286    for (i = 1; i <= loci; i++) {
287      if (eoln(infile)) 
288        scan_eoln(infile);
289      fscanf(infile, "%ld", &alleles[i - 1]);
290      if (alleles[i - 1] <= 0) {
291    printf("ERROR: Bad number of alleles: %ld at locus %ld\n", alleles[i-1], i);
292        exxit(-1);
293      }
294      totalleles += alleles[i - 1];
295      if (printdata)
296        fprintf(outfile, "%4ld", alleles[i - 1]);
297    }
298    locus = (long *)Malloc(totalleles*sizeof(long));
299    totalleles = 0;
300    for (i = 1; i <= loci; i++) {
301      for (j = totalleles; j < (totalleles + alleles[i - 1]); j++)
302        locus[j] = i;
303      totalleles += alleles[i - 1];
304    }
305    df = totalleles - loci;
306  }
307  allocview(&curtree, nonodes2, totalleles);
308  if (!usertree) {
309    allocview(&bestree, nonodes2, totalleles);
310    allocview(&priortree, nonodes2, totalleles);
311    if (njumble > 1)
312      allocview(&bestree2, nonodes2, totalleles);
313  }
314  for (i = 0; i < spp; i++)
315    x[i] = (phenotype3)Malloc(totalleles*sizeof(double));
316  if (usertree)
317    for (i = 0; i < maxtrees; i++)
318      l0gf[i] = (double *)Malloc(totalleles*sizeof(double));
319  if (printdata)
320    putc('\n', outfile);
321}  /* getalleles */
322
323
324void inputdata()
325{
326  /* read species data */
327  long i, j, k, l, m, n, p;
328  double sum;
329
330  if (printdata) {
331    fprintf(outfile, "\nName");
332    if (contchars)
333      fprintf(outfile, "                       Phenotypes\n");
334    else
335      fprintf(outfile, "                 Gene Frequencies\n");
336    fprintf(outfile, "----");
337    if (contchars)
338      fprintf(outfile, "                       ----------\n");
339    else
340      fprintf(outfile, "                 ---- -----------\n");
341    putc('\n', outfile);
342    if (!contchars) {
343      for (j = 1; j <= nmlngth - 8; j++)
344        putc(' ', outfile);
345      fprintf(outfile, "locus:");
346      p = 1;
347      for (j = 1; j <= loci; j++) {
348        if (all)
349          n = alleles[j - 1];
350        else
351          n = alleles[j - 1] - 1;
352        for (k = 1; k <= n; k++) {
353          fprintf(outfile, "%10ld", j);
354          if (p % 6 == 0 && (all || p < df)) {
355            putc('\n', outfile);
356            for (l = 1; l <= nmlngth - 2; l++)
357              putc(' ', outfile);
358          }
359          p++;
360        }
361      }
362      fprintf(outfile, "\n\n");
363    }
364  }
365  for (i = 0; i < spp; i++) {
366    scan_eoln(infile);
367    initname(i);
368    if (printdata)
369      for (j = 0; j < nmlngth; j++)
370        putc(nayme[i][j], outfile);
371    m = 1;
372    p = 1;
373    for (j = 1; j <= loci; j++) {
374      sum = 0.0;
375      if (contchars)
376        n = 1;
377      else if (all)
378        n = alleles[j - 1];
379      else
380        n = alleles[j - 1] - 1;
381      for (k = 1; k <= n; k++) {
382        if (eoln(infile)) 
383          scan_eoln(infile);
384        fscanf(infile, "%lf", &x[i][m - 1]);
385        sum += x[i][m - 1];
386        if (!contchars && x[i][m - 1] < 0.0) {
387          printf("\n\nERROR: locus %ld in species %ld: an allele", j, i+1);
388          printf(" frequency is negative\n");
389          exxit(-1);
390        }
391        if (printdata) {
392          fprintf(outfile, "%10.5f", x[i][m - 1]);
393          if (p % 6 == 0 && (all || p < df)) {
394            putc('\n', outfile);
395            for (l = 1; l <= nmlngth; l++)
396              putc(' ', outfile);
397          }
398        }
399        if (!contchars) {
400          if (x[i][m - 1] >= epsilon1)
401            x[i][m - 1] = sqrt(x[i][m - 1]);
402        }
403        p++;
404        m++;
405      }
406      if (all && fabs(sum - 1.0) > epsilon2) {
407        printf(
408      "\n\nERROR: Locus %ld in species %ld: frequencies do not add up to 1\n\n",
409                  j, i + 1);
410        exxit(-1);
411        }
412      if (!all && !contchars) {
413        x[i][m - 1] = 1.0 - sum;
414        if (x[i][m - 1] >= epsilon1)
415          x[i][m - 1] = sqrt(x[i][m - 1]);
416        if (x[i][m - 1] < 0.0) {
417          if (x[i][m - 1] > -epsilon2) {
418            for (l = 0; l <= m - 2; l++)
419              x[i][l] /= sqrt(sum);
420            x[i][m - 1] = 0.0;
421          } else {
422            printf("\n\nERROR: Locus %ld in species %ld: ", j, i + 1);
423            printf("frequencies add up to more than 1\n\n");
424            exxit(-1);
425          }
426        }
427        m++;
428      }
429    }
430    if (printdata)
431      putc('\n', outfile);
432  }
433  scan_eoln(infile);
434  if (printdata)
435    putc('\n', outfile);
436}  /* inputdata */
437
438
439void getinput()
440{
441  /* reads the input data */
442  getalleles();
443  inputdata();
444}  /* getinput */
445
446
447void sumlikely(node *p, node *q, double *sum)
448{
449  /* sum contribution to likelihood over forks in tree */
450  long i;
451  double term, sumsq, vee;
452  double TEMP;
453
454  if (!p->tip)
455    sumlikely(p->next->back, p->next->next->back, sum);
456  if (!q->tip)
457    sumlikely(q->next->back, q->next->next->back, sum);
458  if (p->back == q)
459    vee = p->v;
460  else
461    vee = p->v + q->v;
462  vee += p->deltav + q->deltav;
463  if (vee <= 1.0e-10) {
464    printf("ERROR: check for two identical species ");
465    printf("and eliminate one from the data\n");
466    exxit(-1);
467  }
468  sumsq = 0.0;
469  if (usertree && which <= maxtrees) {
470    for (i = 0; i < loci; i++)
471      l0gf[which - 1]
472        [i] += (1 - alleles[i]) * log(vee) / 2.0;
473  }
474  for (i = 0; i < totalleles; i++) {
475    TEMP = p->view[i] - q->view[i];
476    term = TEMP * TEMP;
477    if (usertree && which <= maxtrees)
478      l0gf[which - 1]
479        [locus[i] - 1] -= term / (2.0 * vee);
480    sumsq += term;
481  }
482  (*sum) += df * log(vee) / -2.0 - sumsq / (2.0 * vee);
483}  /* sumlikely */
484
485
486double evaluate(tree *t)
487{
488  /* evaluate likelihood of a tree */
489  long i;
490  double sum;
491
492  sum = 0.0;
493  if (usertree && which <= maxtrees) {
494    for (i = 0; i < loci; i++)
495      l0gf[which - 1][i] = 0.0;
496  }
497  sumlikely(t->start->back, t->start, &sum);
498  if (usertree) {
499    l0gl[which - 1] = sum;
500    if (which == 1) {
501      maxwhich = 1;
502      maxlogl = sum;
503    } else if (sum > maxlogl) {
504      maxwhich = which;
505      maxlogl = sum;
506    }
507  }
508  t->likelihood = sum;
509  return sum;
510}  /* evaluate */
511
512
513double distance(node *p, node *q)
514{
515  /* distance between two nodes */
516  long i;
517  double sum;
518  double TEMP;
519
520  sum = 0.0;
521  for (i = 0; i < totalleles; i++) {
522    TEMP = p->view[i] - q->view[i];
523    sum += TEMP * TEMP;
524  }
525  return sum;
526}  /* distance */
527
528
529void makedists(node *p)
530{
531  long i;
532  node *q;
533  /* compute distances among three neighbors of a node */
534
535
536  for (i = 1; i <= 3; i++) {
537    q = p->next;
538    p->dist = distance(p->back, q->back);
539    p = q;
540  }
541}  /* makedists */
542
543
544void makebigv(node *p, boolean *negatives)
545{
546  /* make new branch length */
547  long i;
548  node *temp, *q, *r;
549
550  q = p->next;
551  r = q->next;
552  *negatives = false;
553  for (i = 1; i <= 3; i++) {
554    p->bigv = p->v + p->back->deltav;
555    if (p->iter) {
556      p->bigv = (p->dist + r->dist - q->dist) / (df * 2);
557      p->back->bigv = p->bigv;
558      if (p->bigv < p->back->deltav)
559        *negatives = true;
560    }
561    temp = p;
562    p = q;
563    q = r;
564    r = temp;
565  }
566}  /* makebigv */
567
568
569void correctv(node *p)
570{
571  /* iterate branch lengths if some are to be zero */
572  node *q, *r, *temp;
573  long i, j;
574  double f1, f2, vtot;
575
576  q = p->next;
577  r = q->next;
578  for (i = 1; i <= smoothings; i++) {
579    for (j = 1; j <= 3; j++) {
580      vtot = q->bigv + r->bigv;
581      if (vtot > 0.0)
582        f1 = q->bigv / vtot;
583      else
584        f1 = 0.5;
585      f2 = 1.0 - f1;
586      p->bigv = (f1 * r->dist + f2 * p->dist - f1 * f2 * q->dist) / df;
587      p->bigv -= vtot * f1 * f2;
588      if (p->bigv < p->back->deltav)
589        p->bigv = p->back->deltav;
590      p->back->bigv = p->bigv;
591      temp = p;
592      p = q;
593      q = r;
594      r = temp;
595    }
596  }
597}  /* correctv */
598
599
600void littlev(node *p)
601{
602  /* remove part of it that belongs to other barnches */
603  long i;
604
605  for (i = 1; i <= 3; i++) {
606    if (p->iter)
607      p->v = p->bigv - p->back->deltav;
608    if (p->back->iter)
609      p->back->v = p->v;
610    p = p->next;
611  }
612}  /* littlev */
613
614
615void nuview(node *p)
616{
617  /* renew information about subtrees */
618  long i, j;
619  node *q, *r, *a, *b, *temp;
620  double v1, v2, vtot, f1, f2;
621
622  q = p->next;
623  r = q->next;
624  for (i = 1; i <= 3; i++) {
625    a = q->back;
626    b = r->back;
627    v1 = q->bigv;
628    v2 = r->bigv;
629    vtot = v1 + v2;
630    if (vtot > 0.0)
631      f1 = v2 / vtot;
632    else
633      f1 = 0.5;
634    f2 = 1.0 - f1;
635    for (j = 0; j <totalleles; j++)
636      p->view[j] = f1 * a->view[j] + f2 * b->view[j];
637    p->deltav = v1 * f1;
638    temp = p;
639    p = q;
640    q = r;
641    r = temp;
642  }
643}  /* nuview */
644
645
646void update(node *p)
647{
648  /* update branch lengths around a node */
649  boolean negatives;
650
651  if (p->tip)
652    return;
653  makedists(p);
654  makebigv(p,&negatives);
655  if (negatives)
656    correctv(p);
657  littlev(p);
658  nuview(p);
659}  /* update */
660
661
662void smooth(node *p)
663{
664  /* go through tree getting new branch lengths and views */
665  if (p->tip)
666    return;
667  update(p);
668  smooth(p->next->back);
669  smooth(p->next->next->back);
670}  /* smooth */
671
672
673void insert_(node *p, node *q)
674{
675  /* put p and q together and iterate info. on resulting tree */
676  long i;
677
678  hookup(p->next->next, q->back);
679  hookup(p->next, q);
680  for (i = 1; i <= smoothings; i++) {
681    smooth(p);
682    smooth(p->back);
683  }
684}  /* insert_ */
685
686
687void copynode(node *c, node *d)
688{
689  /* make a copy of a node */
690  memcpy(d->view, c->view, totalleles*sizeof(double));
691  d->v = c->v;
692  d->iter = c->iter;
693  d->deltav = c->deltav;
694  d->bigv = c->bigv;
695  d->dist = c->dist;
696  d->xcoord = c->xcoord;
697  d->ycoord = c->ycoord;
698  d->ymin = c->ymin;
699  d->ymax = c->ymax;
700}  /* copynode */
701
702
703void copy_(tree *a, tree *b)
704{
705  /* make a copy of a tree */
706  long i, j;
707  node *p, *q;
708
709  for (i = 0; i < spp; i++) {
710    copynode(a->nodep[i], b->nodep[i]);
711    if (a->nodep[i]->back) {
712      if (a->nodep[i]->back == a->nodep[a->nodep[i]->back->index - 1])
713        b->nodep[i]->back = b->nodep[a->nodep[i]->back->index - 1];
714      else if (a->nodep[i]->back == a->nodep[a->nodep[i]->back->index - 1]->next)
715        b->nodep[i]->back = b->nodep[a->nodep[i]->back->index - 1]->next;
716      else
717        b->nodep[i]->back = b->nodep[a->nodep[i]->back->index - 1]->next->next;
718    }
719    else b->nodep[i]->back = NULL;
720  }
721  for (i = spp; i < nonodes2; i++) {
722    p = a->nodep[i];
723    q = b->nodep[i];
724    for (j = 1; j <= 3; j++) {
725      copynode(p, q);
726      if (p->back) {
727        if (p->back == a->nodep[p->back->index - 1])
728          q->back = b->nodep[p->back->index - 1];
729        else if (p->back == a->nodep[p->back->index - 1]->next)
730          q->back = b->nodep[p->back->index - 1]->next;
731        else
732          q->back = b->nodep[p->back->index - 1]->next->next;
733      }
734      else
735        q->back = NULL;
736      p = p->next;
737      q = q->next;
738    }
739  }
740  b->likelihood = a->likelihood;
741  b->start = a->start;
742}  /* copy_ */
743
744
745void inittip(long m, tree *t)
746{
747  /* initialize branch lengths and views in a tip */
748  node *tmp;
749
750  tmp = t->nodep[m - 1];
751  memcpy(tmp->view, x[m - 1], totalleles*sizeof(double));
752  tmp->deltav = 0.0;
753  tmp->v = 0.0;
754}  /* inittip */
755
756
757void buildnewtip(long m, tree *t, long nextsp)
758{
759  /* initialize and hook up a new tip */
760  node *p;
761
762  inittip(m, t);
763  p = t->nodep[nextsp + spp - 3];
764  hookup(t->nodep[m - 1], p);
765}  /* buildnewtip */
766
767
768void buildsimpletree(tree *t)
769{
770  /* make and initialize a three-species tree */
771  inittip(enterorder[0], t);
772  inittip(enterorder[1], t);
773  hookup(t->nodep[enterorder[0] - 1], t->nodep[enterorder[1] - 1]);
774  buildnewtip(enterorder[2], t, nextsp);
775  insert_(t->nodep[enterorder[2] - 1]->back, t->nodep[enterorder[0] - 1]);
776}  /* buildsimpletree */
777
778
779void addtraverse(node *p, node *q, boolean contin)
780{
781  /* traverse through a tree, finding best place to add p */
782  insert_(p, q);
783  numtrees++;
784  if (evaluate(&curtree) > bestree.likelihood)
785    copy_(&curtree, &bestree);
786  copy_(&priortree, &curtree);
787  if (!q->tip && contin) {
788    addtraverse(p, q->next->back, contin);
789    addtraverse(p, q->next->next->back, contin);
790  }
791}  /* addtraverse */
792
793
794void re_move(node **p, node **q)
795{
796  /* remove p and record in q where it was */
797  *q = (*p)->next->back;
798  hookup(*q, (*p)->next->next->back);
799  (*p)->next->back = NULL;
800  (*p)->next->next->back = NULL;
801  update(*q);
802  update((*q)->back);
803}  /* re_move */
804
805
806void rearrange(node *p)
807{
808  /* rearranges the tree, globally or locally */
809  node *q, *r;
810
811  if (!p->tip && !p->back->tip) {
812    r = p->next->next;
813    re_move(&r, &q );
814    copy_(&curtree, &priortree);
815    addtraverse(r, q->next->back, (boolean)(global && (nextsp == spp)));
816    addtraverse(r, q->next->next->back, (boolean)(global && (nextsp == spp)));
817    copy_(&bestree, &curtree);
818    if (global && nextsp == spp && progress) {
819      putchar('.');
820      fflush(stdout);
821    }
822    if (global && nextsp == spp && !succeeded) {
823      if (r->back->tip) {
824        r = r->next->next;
825        re_move(&r, &q );
826        q = q->back;
827        copy_(&curtree, &priortree);
828        if (!q->tip) {
829          addtraverse(r, q->next->back, true);
830          addtraverse(r, q->next->next->back, true);
831        }
832        q = q->back;
833        if (!q->tip) {
834          addtraverse(r, q->next->back, true);
835          addtraverse(r, q->next->next->back, true);
836        }
837        copy_(&bestree, &curtree);
838      }
839    }
840  }
841  if (!p->tip) {
842    rearrange(p->next->back);
843    rearrange(p->next->next->back);
844  }
845}  /* rearrange */
846
847
848void coordinates(node *p, double lengthsum, long *tipy, double *tipmax)
849{
850  /* establishes coordinates of nodes */
851  node *q, *first, *last;
852
853  if (p->tip) {
854    p->xcoord = lengthsum;
855    p->ycoord = *tipy;
856    p->ymin = *tipy;
857    p->ymax = *tipy;
858    (*tipy) += down;
859    if (lengthsum > (*tipmax))
860      (*tipmax) = lengthsum;
861    return;
862  }
863  q = p->next;
864  do {
865    coordinates(q->back, lengthsum + q->v, tipy,tipmax);
866    q = q->next;
867  } while ((p == curtree.start || p != q) &&
868           (p != curtree.start || p->next != q));
869  first = p->next->back;
870  q = p;
871  while (q->next != p)
872    q = q->next;
873  last = q->back;
874  p->xcoord = lengthsum;
875  if (p == curtree.start)
876    p->ycoord = p->next->next->back->ycoord;
877  else
878    p->ycoord = (first->ycoord + last->ycoord) / 2;
879  p->ymin = first->ymin;
880  p->ymax = last->ymax;
881}  /* coordinates */
882
883
884void drawline(long i, double scale)
885{
886  /* draws one row of the tree diagram by moving up tree */
887  node *p, *q;
888  long n, j;
889  boolean extra;
890  node *r, *first = NULL, *last = NULL;
891  boolean done;
892
893  p = curtree.start;
894  q = curtree.start;
895  extra = false;
896  if (i == (long)p->ycoord && p == curtree.start) {
897    if (p->index - spp >= 10)
898      fprintf(outfile, " %2ld", p->index - spp);
899    else
900      fprintf(outfile, "  %ld", p->index - spp);
901    extra = true;
902  } else
903    fprintf(outfile, "  ");
904  do {
905    if (!p->tip) {
906      r = p->next;
907      done = false;
908      do {
909        if (i >= (long)r->back->ymin && i <= (long)r->back->ymax) {
910          q = r->back;
911          done = true;
912        }
913        r = r->next;
914      } while (!(done || (p != curtree.start && r == p) ||
915                 (p == curtree.start && r == p->next)));
916      first = p->next->back;
917      r = p;
918      while (r->next != p)
919        r = r->next;
920      last = r->back;
921      if (p == curtree.start)
922        last = p->back;
923    }
924    done = (p->tip || p == q);
925    n = (long)(scale * (q->xcoord - p->xcoord) + 0.5);
926    if (n < 3 && !q->tip)
927      n = 3;
928    if (extra) {
929      n--;
930      extra = false;
931    }
932    if ((long)q->ycoord == i && !done) {
933      if ((long)p->ycoord != (long)q->ycoord)
934        putc('+', outfile);
935      else
936        putc('-', outfile);
937      if (!q->tip) {
938        for (j = 1; j <= n - 2; j++)
939          putc('-', outfile);
940        if (q->index - spp >= 10)
941          fprintf(outfile, "%2ld", q->index - spp);
942        else
943          fprintf(outfile, "-%ld", q->index - spp);
944        extra = true;
945      } else {
946        for (j = 1; j < n; j++)
947          putc('-', outfile);
948      }
949    } else if (!p->tip) {
950      if ((long)last->ycoord > i && (long)first->ycoord < i
951           && i != (long)p->ycoord) {
952        putc('!', outfile);
953        for (j = 1; j < n; j++)
954          putc(' ', outfile);
955      } else {
956        for (j = 1; j <= n; j++)
957          putc(' ', outfile);
958      }
959    } else {
960      for (j = 1; j <= n; j++)
961        putc(' ', outfile);
962    }
963    if (q != p)
964      p = q;
965  } while (!done);
966  if ((long)p->ycoord == i && p->tip) {
967    for (j = 0; j < nmlngth; j++)
968      putc(nayme[p->index - 1][j], outfile);
969  }
970  putc('\n', outfile);
971}  /* drawline */
972
973
974void printree()
975{
976  /* prints out diagram of the tree */
977  long i;
978  long tipy;
979  double tipmax,scale;
980
981  if (!treeprint)
982    return;
983  putc('\n', outfile);
984  tipy = 1;
985  tipmax = 0.0;
986  coordinates(curtree.start, 0.0, &tipy,&tipmax);
987  scale = over / (tipmax + 0.0001);
988  for (i = 1; i <= (tipy - down); i++)
989    drawline(i,scale);
990  putc('\n', outfile);
991}  /* printree */
992
993
994void treeout(node *p)
995{
996  /* write out file with representation of final tree */
997  long i, n, w;
998  Char c;
999  double x;
1000
1001  if (p->tip) {
1002    n = 0;
1003    for (i = 1; i <= nmlngth; i++) {
1004      if (nayme[p->index - 1][i - 1] != ' ')
1005        n = i;
1006    }
1007    for (i = 0; i < n; i++) {
1008      c = nayme[p->index - 1][i];
1009      if (c == ' ')
1010        c = '_';
1011      putc(c, outtree);
1012    }
1013    col += n;
1014  } else {
1015    putc('(', outtree);
1016    col++;
1017    treeout(p->next->back);
1018    putc(',', outtree);
1019    col++;
1020    if (col > 55) {
1021      putc('\n', outtree);
1022      col = 0;
1023    }
1024    treeout(p->next->next->back);
1025    if (p == curtree.start) {
1026      putc(',', outtree);
1027      col++;
1028      if (col > 45) {
1029        putc('\n', outtree);
1030        col = 0;
1031      }
1032      treeout(p->back);
1033    }
1034    putc(')', outtree);
1035    col++;
1036  }
1037  x = p->v;
1038  if (x > 0.0)
1039    w = (long)(0.43429448222 * log(x));
1040  else if (x == 0.0)
1041    w = 0;
1042  else
1043    w = (long)(0.43429448222 * log(-x)) + 1;
1044  if (w < 0)
1045    w = 0;
1046  if (p == curtree.start)
1047    fprintf(outtree, ";\n");
1048  else {
1049    fprintf(outtree, ":%*.5f", (int)w + 7, x);
1050    col += w + 8;
1051  }
1052}  /* treeout */
1053
1054
1055void describe(node *p, double chilow, double chihigh)
1056{
1057  /* print out information for one branch */
1058  long i;
1059  node *q;
1060  double bigv, delta;
1061
1062  q = p->back;
1063  fprintf(outfile, "%3ld       ", q->index - spp);
1064  if (p->tip) {
1065    for (i = 0; i < nmlngth; i++)
1066      putc(nayme[p->index - 1][i], outfile);
1067  } else
1068    fprintf(outfile, "%4ld      ", p->index - spp);
1069  fprintf(outfile, "%15.5f", q->v);
1070  delta = p->deltav + p->back->deltav;
1071  bigv = p->v + delta;
1072  if (p->iter)
1073     fprintf(outfile, "   (%12.5f,%12.5f)",
1074             chilow * bigv - delta, chihigh * bigv - delta);
1075  fprintf(outfile, "\n");
1076  if (!p->tip) {
1077    describe(p->next->back, chilow,chihigh);
1078    describe(p->next->next->back, chilow,chihigh);
1079  }
1080}  /* describe */
1081
1082
1083void summarize(void)
1084{
1085  /* print out branch lengths etc. */
1086  double chilow,chihigh;
1087
1088  fprintf(outfile, "\nremember: ");
1089  if (outgropt)
1090    fprintf(outfile, "(although rooted by outgroup) ");
1091  fprintf(outfile, "this is an unrooted tree!\n\n");
1092  fprintf(outfile, "Ln Likelihood = %11.5f\n", curtree.likelihood);
1093  if (df == 1) {
1094    chilow = 0.000982;
1095    chihigh = 5.02389;
1096  } else if (df == 2) {
1097    chilow = 0.05064;
1098    chihigh = 7.3777;
1099  } else {
1100    chilow = 1.0 - 2.0 / (df * 9);
1101    chihigh = chilow;
1102    chilow -= 1.95996 * sqrt(2.0 / (df * 9));
1103    chihigh += 1.95996 * sqrt(2.0 / (df * 9));
1104    chilow *= chilow * chilow;
1105    chihigh *= chihigh * chihigh;
1106  }
1107  fprintf(outfile, "\nBetween     And             Length");
1108  fprintf(outfile, "      Approx. Confidence Limits\n");
1109  fprintf(outfile, "-------     ---             ------");
1110  fprintf(outfile, "      ------- ---------- ------\n");
1111  describe(curtree.start->next->back, chilow,chihigh);
1112  describe(curtree.start->next->next->back, chilow,chihigh);
1113  describe(curtree.start->back, chilow, chihigh);
1114  fprintf(outfile, "\n\n");
1115  if (trout) {
1116    col = 0;
1117    treeout(curtree.start);
1118  }
1119}  /* summarize */
1120
1121
1122void nodeinit(node *p)
1123{
1124  /* initialize a node */
1125  node *q, *r;
1126  long i;
1127
1128  if (p->tip)
1129    return;
1130  q = p->next->back;
1131  r = p->next->next->back;
1132  nodeinit(q);
1133  nodeinit(r);
1134  for (i = 0; i < totalleles; i++)
1135    p->view[i] = 0.5 * q->view[i] + 0.5 * r->view[i];
1136  if (p->iter)
1137    p->v = 0.1;
1138  if (p->back->iter)
1139    p->back->v = 0.1;
1140}  /* nodeinit */
1141
1142
1143void initrav(node *p)
1144{
1145  /* traverse to initialize */
1146  if (p->tip)
1147    nodeinit(p->back);
1148  else {
1149    initrav(p->next->back);
1150    initrav(p->next->next->back);
1151  }
1152}  /* initrav */
1153
1154
1155void treevaluate()
1156{
1157  /* evaluate user-defined tree, iterating branch lengths */
1158  long i;
1159
1160  initrav(curtree.start);
1161  initrav(curtree.start->back);
1162  for (i = 1; i <= smoothings * 4; i++)
1163    smooth(curtree.start);
1164  evaluate(&curtree);
1165}  /* treevaluate */
1166
1167
1168void maketree()
1169{
1170  /* construct the tree */
1171  long i;
1172
1173  if (usertree) {
1174    openfile(&intree,INTREE,"input tree file", "r",progname,intreename);
1175    numtrees = countsemic(&intree);
1176    if (treeprint) {
1177      fprintf(outfile, "User-defined tree");
1178      if (numtrees > 1)
1179        putc('s', outfile);
1180      putc('\n', outfile);
1181    }
1182    setuptree(&curtree, nonodes2);
1183    for (which = 1; which <= spp; which++)
1184      inittip(which, &curtree);
1185    which = 1;
1186    while (which <= numtrees) {
1187      treeread2 (intree, &curtree.start, curtree.nodep,
1188        lengths, &trweight, &goteof, &haslengths, &spp);
1189      curtree.start = curtree.nodep[outgrno - 1]->back;
1190      treevaluate();
1191      printree();
1192      summarize();
1193      which++;
1194    }
1195    FClose(intree);
1196    if (numtrees > 1 && loci > 1 ) {
1197      weight = (long *)Malloc(loci*sizeof(long));
1198      for (i = 0; i < loci; i++)
1199        weight[i] = 1;
1200      standev2(numtrees, maxwhich, 0, loci-1, maxlogl, l0gl, l0gf, seed);
1201      free(weight);
1202      fprintf(outfile, "\n\n");
1203    }
1204  } else {
1205    if (jumb == 1) {
1206      setuptree(&curtree, nonodes2);
1207      setuptree(&priortree, nonodes2);
1208      setuptree(&bestree, nonodes2);
1209      if (njumble > 1) 
1210        setuptree(&bestree2, nonodes2);
1211    }
1212    for (i = 1; i <= spp; i++)
1213      enterorder[i - 1] = i;
1214    if (jumble)
1215      randumize(seed, enterorder);
1216    nextsp = 3;
1217    buildsimpletree(&curtree);
1218    curtree.start = curtree.nodep[enterorder[0] - 1]->back;
1219    if (jumb == 1) numtrees = 1;
1220    nextsp = 4;
1221    if (progress) {
1222      printf("Adding species:\n");
1223      writename(0, 3, enterorder);
1224#ifdef WIN32
1225      phyFillScreenColor();
1226#endif
1227    }
1228    while (nextsp <= spp) {
1229      buildnewtip(enterorder[nextsp - 1], &curtree, nextsp);
1230      copy_(&curtree, &priortree);
1231      bestree.likelihood = -99999.0;
1232      addtraverse(curtree.nodep[enterorder[nextsp - 1] - 1]->back,
1233                  curtree.start, true );
1234      copy_(&bestree, &curtree);
1235      if (progress) {
1236        writename(nextsp - 1, 1, enterorder);
1237#ifdef WIN32
1238        phyFillScreenColor();
1239#endif
1240      }
1241      if (global && nextsp == spp) {
1242        if (progress) {
1243          printf("\nDoing global rearrangements\n");
1244          printf("  !");
1245          for (i = 1; i <= spp - 2; i++)
1246            putchar('-');
1247          printf("!\n");
1248          printf("   ");
1249        }
1250      }
1251      succeeded = true;
1252      while (succeeded) {
1253        succeeded = false;
1254        rearrange(curtree.start);
1255        if (global && nextsp == spp)
1256          putc('\n', outfile);
1257      }
1258      if (global && nextsp == spp && progress)
1259        putchar('\n');
1260      if (njumble > 1) {
1261        if (jumb == 1 && nextsp == spp)
1262          copy_(&bestree, &bestree2);
1263        else if (nextsp == spp) {
1264          if (bestree2.likelihood < bestree.likelihood)
1265            copy_(&bestree, &bestree2);
1266        }
1267      }
1268      if (nextsp == spp && jumb == njumble) {
1269        if (njumble > 1) copy_(&bestree2, &curtree);
1270        curtree.start = curtree.nodep[outgrno - 1]->back;
1271        printree();
1272        summarize();
1273      }
1274      nextsp++;
1275    }
1276  }
1277  if ( jumb < njumble)
1278    return;
1279  if (progress) {
1280    printf("\n\nOutput written to file \"%s\"\n\n", outfilename);
1281    if (trout)
1282      printf("Tree also written onto file \"%s\"\n\n", outtreename);
1283  }
1284  freeview(&curtree, nonodes2);
1285  if (!usertree) {
1286    freeview(&bestree, nonodes2);
1287    freeview(&priortree, nonodes2);
1288  }
1289  for (i = 0; i < spp; i++)
1290    free(x[i]);
1291  if (!contchars)
1292    free(locus);
1293  if (usertree)
1294    for (i = 0; i < maxtrees; i++)
1295      free(l0gf[i]);
1296}  /* maketree */
1297
1298
1299int main(int argc, Char *argv[])
1300{  /* main program */
1301#ifdef MAC
1302  argc = 1;                /* macsetup("Contml","");                */
1303  argv[0] = "Contml";
1304#endif
1305  init(argc, argv);
1306  progname = argv[0];
1307  openfile(&infile,INFILE,"input file", "r",argv[0],infilename);
1308  openfile(&outfile,OUTFILE,"output file", "w",argv[0],outfilename);
1309  ibmpc = IBMCRT;
1310  ansi = ANSICRT;
1311  mulsets = false;
1312  firstset = true;
1313  datasets = 1;
1314  doinit();
1315  if (trout)
1316    openfile(&outtree,OUTTREE,"output tree file", "w",argv[0],outtreename);
1317  for (ith = 1; ith <= datasets; ith++) {
1318    getinput();
1319    if (ith == 1)
1320      firstset = false;
1321    if (datasets > 1) {
1322      fprintf(outfile, "Data set # %ld:\n\n", ith);
1323      if (progress)
1324        printf("\nData set # %ld:\n", ith);
1325    }
1326    for (jumb = 1; jumb <= njumble; jumb++)
1327      maketree();
1328  }
1329  FClose(outfile);
1330  FClose(outtree);
1331  FClose(infile);
1332#ifdef MAC
1333  fixmacfile(outfilename);
1334  fixmacfile(outtreename);
1335#endif
1336  printf("Done.\n\n");
1337#ifdef WIN32
1338  phyRestoreConsoleAttributes();
1339#endif
1340  return 0;
1341}
1342
Note: See TracBrowser for help on using the repository browser.