fork(1) download
  1. //---------------------------------------------------------------------------
  2. #include <limits.h>
  3. #include <stdio.h>
  4. #include <vector>
  5. #include <math.h>
  6. #include "wave.hpp"
  7.  
  8. //---------------------------------------------------------------------------
  9. using namespace std;
  10. #define DPI (2*M_PI)
  11.  
  12. vector<double> Re;// [出力] 実数部
  13. vector<double> Im;// [出力] 虚数部
  14. void dft(MONO_PCM& pcm,double st, double ed)
  15. {
  16. // dft
  17. double N = ed-st;
  18. int NN = N;
  19. int* a = &pcm.s[(int)st];
  20. int ptr1=0;
  21. int ptr2=0;
  22. Re.clear();
  23. Im.clear();
  24. for( int fq=0; fq<NN; fq++ )
  25. {
  26. double Re_sum = 0;
  27. double Im_sum = 0;
  28. for( int i=0; i<NN; ++i){
  29. double tht = DPI*fq*i/N;
  30. Re_sum += a[i] * cos( tht );
  31. Im_sum += a[i] * -sin( tht );
  32. }
  33. Re.push_back( Re_sum );
  34. Im.push_back( Im_sum );
  35. }
  36. return;
  37. }
  38. void idft(MONO_PCM& pcm,double N,FILE* ws)
  39. {
  40. int NN = N;
  41. int maxsamp=20;
  42. vector<int> rank;
  43. for( int fq=0; fq<NN; fq++ ){
  44. rank.push_back(fq);
  45. }
  46. for( int i = 0 ; i < NN-1 ; i++ ){
  47. for( int j = i+1; j < NN ; j++ ){
  48. if( Im[rank[i]]*Im[rank[i]] < Im[rank[j]]*Im[rank[j]] ){
  49. int temp = rank[i];
  50. rank[i] = rank[j];
  51. rank[j] = temp;
  52. }
  53. }
  54. }
  55. for( int i=0; i<5; i++ ){
  56. printf("%lf ",Im[rank[i]]);
  57. }
  58. printf( "\n");
  59. //周波数でソート
  60. for( int i = 0 ; i < maxsamp-1 ; i++ ){
  61. for( int j = i+1; j < maxsamp ; j++ ){
  62. if( rank[i] > rank[j] ){
  63. int temp = rank[i];
  64. rank[i] = rank[j];
  65. rank[j] = temp;
  66. }
  67. }
  68. }
  69. for( int i=0; i<maxsamp; i++ ){
  70. double ffq = rank[i];
  71. fprintf(ws,"%s%lf",((i==0)?"":","),ffq*44100/N);
  72. }
  73. for( int i = 0 ; i <maxsamp ; i++ ){
  74. int ii = rank[i];
  75. fprintf(ws,"%s%lf",((i==0)?",":","),Im[ii]);
  76. }
  77. fprintf(ws,",%lf\n",N);
  78.  
  79. for( int fq=0; fq<NN; fq++ )
  80. {
  81. double Re_sum = 0;
  82. double Im_sum = 0;
  83. for( int i = 0 ; i <maxsamp ; i++ ){
  84. int ii = rank[i];
  85. double tht = DPI*fq*ii*44100/N/44100;
  86. //Re_sum += Im[ii]*sin(tht);
  87. Re_sum += //Re[ii] * cos(tht)
  88. -Im[ii] * sin(tht);
  89. }
  90. pcm.s.push_back(Re_sum/N);
  91. }
  92. return;
  93. }
  94. double f(MONO_PCM& pcm, double st,double ed)
  95. {
  96. // dft
  97. double N = ed-st;
  98. int NN = N;
  99. int ist = st;
  100. int ied = ed;
  101. int* a = &pcm.s[0];
  102. //Re.clear();
  103. //Im.clear();
  104. double Im_sum_all=0;
  105. for( int fq=0; fq<NN; fq++ )
  106. {
  107. double Re_sum = 0;
  108. double Im_sum = 0;
  109. for( int i=0; i<NN; i++){
  110. double tht = DPI*fq*i/N;
  111. Re_sum += a[i+ist] * cos( tht );
  112. //Im_sum += a[i+ist] * -sin( tht );
  113. }
  114. Im_sum_all += sqrt(Re_sum/N*Re_sum/N);
  115. }
  116. return Im_sum_all;
  117. }
  118.  
  119. int main(int argc, char* argv[])
  120. {
  121. MONO_PCM pcm1;
  122. MONO_PCM pcm3;
  123.  
  124. pcm1.read("hi.wav");
  125. int ptr=0;
  126. const int div=128;
  127. int* dat = &pcm1.s[0];
  128. FILE* ws = fopen("wav.csv","w");
  129.  
  130. //波形最大最小の取得
  131. int min=0;
  132. int max=0;
  133. for( int i = 0 ; i < pcm1.s.size() ; i++ ){
  134. int num = pcm1.s[i];
  135. if( max<num) max = num;
  136. if( min>num) min = num;
  137. }
  138. //最大値の5%を開始と認識
  139. int minmaxlvl = (max-min)*0.1;
  140. int buffer[1024]={0};
  141. int bufptr=0;
  142. int son=0;
  143. int soff=0;
  144. double adf=0;
  145.  
  146. printf( "%d %d\n", min, max);
  147. //無音範囲検知
  148. for( int i = 0 ; i < pcm1.s.size() ; i++ ){
  149. buffer[bufptr++%1024] = dat[i];
  150. min = 0;
  151. max = 0;
  152. for( int j = 0 ; j < 1024 ; j++ ){
  153. if( min>buffer[j]) min = buffer[j];
  154. if( max<buffer[j]) max = buffer[j];
  155. }
  156. //無音検知
  157. if( son == 0 && max-min > minmaxlvl){
  158. while(1){
  159. if( dat[i]<=0 && dat[i+1]>=0) break;
  160. i++;
  161. }
  162. son = i;
  163. }
  164. //終了無音検知
  165. if( son && max-min < minmaxlvl ){
  166. while(1){
  167. if( dat[i-1]<=0 && dat[i]>=0) break;
  168. i++;
  169. }
  170. soff = i;
  171. break;
  172. }
  173. }
  174. printf( "st:%d ed:%d all:%d\n",son,soff,pcm1.s.size());
  175. //開始から終了まで
  176. int cnt = 0;
  177. for( int i = son ; i <=soff ; ){
  178. //1波形抽出
  179. double maxdiff =-10000;
  180. double diff;
  181. int maxptr;
  182. for( int j = 80 ; j < 255 ; j++ ){
  183. diff=0;
  184. for( int k = 0 ; k < j ; k++ ){
  185. diff += dat[i+k]*dat[i+j+k]/j/j;
  186. }
  187. if( diff>maxdiff ){
  188. maxdiff = diff;
  189. maxptr = i+j;
  190. }
  191. }
  192. //終点前後でcos成分が最小となる点を探す
  193. int maxptr1=maxptr;;
  194. for( int k = 0 ; k < 10 ; k++ ){
  195. double base = f(pcm1,i,maxptr1);
  196. if( f(pcm1,i,maxptr-k)<base ){
  197. maxptr1=maxptr-k;
  198. }else if ( f(pcm1,i,maxptr+k)<base ){
  199. maxptr1=maxptr+k;
  200. }
  201. }
  202. maxptr = maxptr1;
  203. int minptr=maxptr;
  204. printf( "ORG:%d-",minptr-i);
  205. double st = i;
  206. double ed = minptr;
  207. dft(pcm1,st,ed);
  208. idft(pcm3,ed-st,ws);
  209. i = ed;
  210. cnt++;
  211. }
  212. fclose( ws );
  213. pcm3.write("hi2.wav");
  214. return 0;
  215. }
  216. //---------------------------------------------------------------------------
  217.  
Compilation error #stdin compilation error #stdout 0s 0KB
stdin
Standard input is empty
compilation info
prog.cpp: In function 'void dft(MONO_PCM&, double, double)':
prog.cpp:19:18: error: invalid use of incomplete type 'class MONO_PCM'
     int* a = &pcm.s[(int)st];
                  ^
prog.cpp:7:7: note: forward declaration of 'class MONO_PCM'
 class MONO_PCM;
       ^
prog.cpp: In function 'void idft(MONO_PCM&, double, FILE*)':
prog.cpp:90:12: error: invalid use of incomplete type 'class MONO_PCM'
         pcm.s.push_back(Re_sum/N);
            ^
prog.cpp:7:7: note: forward declaration of 'class MONO_PCM'
 class MONO_PCM;
       ^
prog.cpp: In function 'double f(MONO_PCM&, double, double)':
prog.cpp:101:18: error: invalid use of incomplete type 'class MONO_PCM'
     int* a = &pcm.s[0];
                  ^
prog.cpp:7:7: note: forward declaration of 'class MONO_PCM'
 class MONO_PCM;
       ^
prog.cpp: In function 'int main(int, char**)':
prog.cpp:121:16: error: aggregate 'MONO_PCM pcm1' has incomplete type and cannot be defined
       MONO_PCM pcm1;
                ^
prog.cpp:122:16: error: aggregate 'MONO_PCM pcm3' has incomplete type and cannot be defined
       MONO_PCM pcm3;
                ^
stdout
Standard output is empty