ページ 1 / 1
無題
Posted: 2007年12月07日(金) 12:17
by マイク
フーリエ変換をしたいのですが、実行したいファイルがEXCELなんでテキストデータへ変換したいと考えています。
そのようなことができるプログラムを教えて下さい。
Re:無題
Posted: 2007年12月07日(金) 12:24
by box
Excelで当該ファイルを開き、csv形式で保存します。
保存したファイルをもとにフーリエ変換を行う
プログラムを書きます。
Excel形式からテキストに変換するプログラムを
書くより楽でしょう。
Re:無題
Posted: 2007年12月07日(金) 13:23
by たかぎ
処理系不明ではどうしようもありませんね。
boxさんが書かれている通り、Excelを操作して、あらかじめCSV等に変換しておくのがよいでしょう。
ちなみに CSV の仕様は
http://www.ietf.org/rfc/rfc4180.txt
です。
ASCIIしか使えないような気がしますが、片目を閉じて読むことをお勧めします。
Re:無題
Posted: 2007年12月07日(金) 15:44
by マイク
一応ファイルはCSVでまとめています。(下記参照)
出力電圧
-3.5058594
-3.3886719
-3.3496094
ファイル名"text.csv"
これを離散フーリエしたいので参考となるプログラムです。
/*
* 離散フーリエ変換(DFT: Discrete Fourier Transform) &
* 逆離散フーリエ変換(IDFT:
Inverse Discrete Fourier Transform)
*/
#include <stdio.h>
#include <math.h>
#define PI 3.1415926
#define MAX 512
void dft(double x[MAX], double y[MAX]);
void inverse_dft(double x[MAX], double y[MAX]);
int main(int argc, char *argv[/url])
{
double x[MAX],y[MAX],value;
int i;
FILE *fp,*fp2;
if(argc!=3){
printf("Usage is ...\n");
printf("trans.exe <input file> <output file>\n");
return(-1);
}
/* ファイル読込み */
if((fp = fopen("text.csv","r"))
== NULL){
return(-1);
}
if((fp2=fopen("outcome.txt","w")) == NULL){
return(-1);
}
for(i=0; i<MAX; i++){
fscanf(fp,"%lf\n",&value);
x = value; /* x :実数成分 */
y = 0; /* y :虚数成分 */
}
/* ここからDFT */
dft(x,y);
for(i=0; i<MAX; i++){
// fprintf(fp2,"%f,%f\n",x,y);
fprintf(fp2,"% .5f,% .5f\n",((double)100/MAX)*i,sqrt(x*x+y*y)*2/MAX);
}
/* ここからIDFT
inverse_dft(x,y);
for(i=0; i<MAX; i++){
printf("%f\t%f\n",x,y);
}*/
fclose(fp);
fclose(fp2);
return(0);
}
void dft(double x[MAX],
double y[MAX])
{
int i,j;
double tmp_x[MAX],tmp_y[MAX];
/* データを一旦コピー
*/
for (i=0; i<MAX; i++) {
tmp_x[i] = x[i];
tmp_y[i] = y[i];
}
for (i=0; i<MAX; i++) {
x[i] = 0;
y[i] = 0;
for (j=0; j<MAX;
j++) {
x[i] += tmp_x[j]*cos(2*PI*i*j/MAX) + tmp_y[j]*sin(2*PI*i*j/MAX);
y[i] += -tmp_x[j]*sin(2*PI*i*j/MAX) + tmp_y[j]*cos(2*PI*i*j/MAX);
}
}
}
void inverse_dft(double x[MAX], double y[MAX])
{
int i,j;
double
tmp_x[MAX],tmp_y[MAX];
/* データを一旦コピー */
for (i=0; i<MAX;
i++) {
tmp_x[i] = x[i];
tmp_y[i] = y[i];
}
for (i=0; i<MAX;
i++) {
x[i] = 0;
y[i] = 0;
for (j=0; j<MAX; j++) {
x[i] +=
tmp_x[j]*cos(2*PI*i*j/MAX) - tmp_x[j]*sin(2*PI*i*j/MAX);
y[i] += tmp_y[j]*sin(2*PI*i*j/MAX)
+ tmp_y[j]*cos(2*PI*i*j/MAX);
}
x[i] /= MAX;
y[i] /= MAX;
}
}
長いですが、計算の箇所は理解できますが、ファイル読み込みの箇所がイマイチ理解できません。
本当にこれでいいのかと思うのですが。。。
何か気づいた点あれば教えてください。
Re:無題
Posted: 2007年12月07日(金) 16:23
by box
> for(i=0; i<MAX; i++){
> fscanf(fp,"%lf\n",&value);
このプログラムでは、512個以上のデータが必要です。
そういう仕様でしょうか?
Re:無題
Posted: 2007年12月07日(金) 22:06
by マイク
そうです。
ある信号を処理しようと思っているので、かなり取っています。
Re:無題
Posted: 2007年12月07日(金) 22:26
by box
それで、今は、
-3.5058594
-3.3886719
-3.3496094
.
.
.
という内容の512個以上のデータを、
for(i=0; i<MAX; i++){
fscanf(fp,"%lf\n",&value);
というコードで読み込んでいるのですよね。
イマイチ理解できないのは、どのあたりでしょうか?
Re:無題
Posted: 2007年12月08日(土) 02:04
by マイク
参考になりそうなものを探していたのでうまく伝わらないかもしれませんが
前半部分の③ポイントです(下記参照)
int main(int argc, char *argv[/url]) ← ①このargc argvの意味は?
{
double x[MAX],y[MAX],value;
int i;
FILE *fp,*fp2;
if(argc!=3){
printf("Usage is ...\n"); ← ②ここのif文の意味は?
printf("trans.exe <input file> <output file>\n");
return(-1);
}
/* ファイル読込み */
if((fp = fopen("text.csv","r"))
== NULL){
return(-1); ← ③これで読み込めるのか?
}
if((fp2=fopen("outcome.txt","w")) == NULL){
return(-1);
}
for(i=0; i<MAX; i++){
fscanf(fp,"%lf\n",&value);
x = value; /* x :実数成分 */
y = 0; /* y :虚数成分 */
}
特に①と③は関連性が高そうで
資料では③の箇所は
...=fopen(argv[1] , "r" ) ...
となっていました。
この点で「これではどのファイルを使うのかが解らないし、かといって main関数で argv[/url]となっているし・・・」
と混乱してしまったのです。
信号解析には必要なので出来る限り理解したいのでアドバイスお願いします。
Re:無題
Posted: 2007年12月08日(土) 10:28
by box
> int main(int argc, char *argv[/url]) ← ①このargc argvの意味は?
実行時に与えるコマンドライン引数のための変数です。
argcは引数の数を、argvは各引数文字列へのポインタの配列です。
このプログラムでは、
プログラム名 入力ファイル名 出力ファイル名 <Enter>
のように実行しますね。このとき、
argc :3
argv[0]:"プログラム名" の先頭文字のアドレス
argv[1]:"入力ファイル名" 同上
argv[2]:"出力ファイル名" 同上
となります。
> if(argc!=3){
> printf("Usage is ...\n"); ← ②ここのif文の意味は?
> printf("trans.exe <input file> <output file>\n");
というわけで、実行時に、
プログラム名 入力ファイル名 出力ファイル名 <Enter>
という形式で入力していなければ、プログラムの使い方を
出力して終了するようになっています。
> /* ファイル読込み */
> if((fp = fopen("text.csv","r"))
> == NULL){
> return(-1); ← ③これで読み込めるのか?
入力ファイルを "test.csv" で固定してよければ、このように書いてください。
ただ、今回の場合はコマンドライン引数で指定したいようですので、
if((fp = fopen(argv[1],"r"))
と書くのが本筋でしょうね。
Re:無題
Posted: 2007年12月08日(土) 11:31
by マイク
よくわかりました!
一度試してみたいと思います。感謝です!