next up previous contents
Next: 付録E 想起した曲をFFTするプログラム Up: 無題 Previous: 付録C 曲を想起させるプログラム

付録D 曲データを周波数に変換するプログラム

/* 想起した曲を周波数に変換するプログラム : syuhasu.c */

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <math.h>

double fl(double x){
  return(-log(x)/(M_LN2 * 5) +1 );
}

int lc(double len){
  if(len<=(fl(12)-fl(16))/2+fl(16)){
    return 2;    /* "16" */
  }else if(len<=(fl(8)-fl(12))/2+fl(12)){
    return 3;    /* "16." */
  }else if(len<=(fl(6)-fl(8))/2+fl(8)){
    return 4;    /* "8" */
  }else if(len<=(fl(4)-fl(6))/2+fl(6)){
    return 6;    /* "8." */
  }else if(len<=(fl(3)-fl(4))/2+fl(4)){
    return 8;    /* "4" */
  }else if(len<=(fl(2)-fl(3))/2+fl(3)){
    return 12;   /* "4." */
  }else if(len<=(fl(1.5)-fl(2))/2+fl(2)){
    return 16;   /* "2" */
  }else if(len<=(1-fl(1.5))/2+fl(1.5)){
    return 24;   /* "2." */
  }else{         /* if(len<=1){ */ 
    return 32;   /* "1" */
  }
}

int rd(double a){
  char buf[10], *s;
  int b;

  sprintf(buf, "%lf", a);

  s=strchr(buf, '.');
  if(s==NULL) return((int)a);
  s++;

  if(*s-'0'<4) b=a;
  else         b=a+1;

  return(b);
}

double pc(double pit, char *s){
  int p;
  double c,h,oct;

  s[0] = '\0';
  pit*=40.0;
  p=rd(pit)/12;

  if(p==-12){
    oct = 0.000122070;
  }else if (p==-11){
    oct = 0.000244140;
  }else if (p==-10){
    oct = 0.000488281;
  }else if (p==-9){
    oct = 0.009765625;
  }else if (p==-8){
    oct = 0.001953125;
  }else if (p==-7){
    oct = 0.0390625;
  }else if (p==-6){
    oct = 0.0078125;
  }else if (p==-5){
    oct = 0.015625;
  }else if (p==-4){
    oct = 0.03125;
  }else if (p==-3){
    oct = 0.0625;
  }else if(p==-2){
    oct = 0.125;
  }else if (p==-1){
    oct = 0.25;
  }else if(p==0){
    oct = 0.5;
  }else if (p==1){
    oct = 1.0;
  }else if (p==2){
    oct = 2.0;
  }else if (p==3){
    oct = 4.0;
  }else if (p==4){
    oct = 8.0;
  }else if (p==5){
    oct = 16.0;
  }else if (p==6){
    oct = 32.0;
  }else if (p==7){
    oct = 64.0;
  }else if (p==8){
    oct = 128.0;
  }else if (p==9){
    oct = 256.0;
  }else if (p==10){
    oct = 512.0;
  }else if (p==11){
    oct = 1024.0;
  }else if (p==12){
    oct = 2048.0;
  }else if (p==13){
    oct = 4096.0;
  }else if (p==14){
    oct = 8192.0;
  }else if (p==15){
    oct = 16384.0;
  }else if (p==16){
    oct = 32768.0;
  }else if (p==17){
    oct = 65536.0;
  }else if (p==18){
    oct = 131072.0;
  }

  p=rd(pit)%12;
  if(p<=1){
    h = 523.2;
  }else if(p<=2){
    h = 554.3;
  }else if(p<=3){
    h = 587.3;
  }else if(p<=4){
    h = 622.2;
  }else if(p<=5){
    h = 659.2;
  }else if(p<=6){
    h = 698.4;
  }else if(p<=7){
    h = 739.9;
  }else if(p<=8){
    h = 783.9;
  }else if(p<=9){
    h = 830.6;
  }else if(p<=10){
    h = 880.0;
  }else if(p<=11){
    h = 932.2;
  }else if(p<=0){
    h = 987.6;
  }
  c = h * oct;
  return(c);
}

main(){
  int c, i, k=1;
  double len, pit, w;
  char a[32], b[32];

  while(fscanf(stdin, "%lf %lf", &len, &pit)!=EOF){
    c = lc(len);
    w = pc(pit,b);
    for(i = 0 ; i < c ; i++ ){
      printf("%0.2f\n",w);
    }
    if( k == 29 ){
      printf("\n",k);
      k = 0;
    }
    k++;
  }
}



Deguchi Toshinori
Thu Jul 13 11:47:42 JST 2000