第8回演習:解答例


演習課題

(1)試験結果のデータ(右クリック-->[対象をファイルに保存] )testdata.txt(100点満点で正の整数)を読み込んで,

  1. 平均値
  2. 標準偏差

を求めるプログラムを作成せよ.データ数はEOFを元に判断すること.
標準偏差などの求め方は, 前期:配列と繰り返しを参考にすること



#include<stdio.h>
#include<math.h>
void main()
{
	int i,n;
	float heikin,bunsan,v;
	float sum1=0.0;
	float sum2=0.0;
	float tensu[512],hensa[512];

	FILE *fp;

	fp=fopen("testdata.txt","r");
	if(fp==NULL){
		printf("ファイルを開けませんでした.¥n");
		return;
	}
	n=0;
	while(!feof(fp)&&n<512){
		fscanf(fp,"%f",&(tensu[n]));
		n++;
	}
	fclose(fp);
	n=n-1;

	for(i=0;i<n;i++){
		sum1=sum1+tensu[i];
	}
	heikin=sum1/(float)n;
	printf("平均値は%fです.¥n",heikin);

	for(i=0;i<n;i++){
		sum2=sum2+(tensu[i]-heikin)*(tensu[i]-heikin);
	}
	bunsan=sum2/(float)n;
	
	v=sqrt(bunsan);
	printf("標準偏差は%fです.¥n",v);
		
}

(2)更に,平均値,標準偏差から各点数の偏差値を求め,ファイルに保存するプログラムを作成せよ.



#include<stdio.h>
#include<math.h>
void main()
{
	int i,n;
	float heikin,bunsan,v;
	float sum1=0.0;
	float sum2=0.0;
	float tensu[512],hensa[512];

	FILE *fp;

	fp=fopen("testdata.txt","r");
	if(fp==NULL){
		printf("ファイルを開けませんでした.¥n");
		return;
	}
	n=0;
	while(!feof(fp)&&n<512){
		fscanf(fp,"%f",&(tensu[n]));
		n++;
	}
	fclose(fp);
	n=n-1;

	for(i=0;i<n;i++){
		sum1=sum1+tensu[i];
	}
	heikin=sum1/(float)n;
	printf("平均値は%fです.¥n",heikin);

	for(i=0;i<n;i++){
		sum2=sum2+(tensu[i]-heikin)*(tensu[i]-heikin);
	}
	bunsan=sum2/(float)n;
	
	v=sqrt(bunsan);
	printf("標準偏差は%fです.¥n",v);

	fp=fopen("hensa.txt","w");
	if(fp==NULL){
		printf("ファイルを作れませんでした.¥n");
		return;
	}
	
	for(i=0;i<n;i++){
		hensa[i]=50.0+10*(tensu[i]-heikin)/v;
		printf("%d番目の偏差値=%f¥n",i+1,hensa[i]);
		fprintf(fp,"%d番目の偏差値=%f¥n",i+1,hensa[i]);
	}
	fclose(fp);
		
}

(3)ファイルから4×4の2次元行列Aを読み込み画面に表示するプログラムを,以下を参考に関数を用いて作成せよ.
行列は、次のファイルを(右クリック-->[対象をファイルに保存])で作成したプログラムと同じフォルダに入れること.
   [Amat.txt],


#include <stdio.h>

/*4×4の行列をファイルから読み込む関数*/
void read_matrix(char filename[], float mat[4][4])
{
	int i,j;
	FILE* fp;
	
	fp = fopen(filename,"r");
	
	if(fp == NULL) {
		printf("ファイルを開くことが出来ませんでした.¥n");
		return;
	}
	
	for(i=0;i<4;i++){
		for(j=0;j<4;j++){
			fscanf(fp,"%f",&mat[i][j]);
		}
	}
	
	fclose(fp);

}

/*4×4の行列を表示する関数*/
void print_matrix(float mat[4][4])
{
	int i,j;
	
	for(i=0;i<4;i++){
		for(j=0;j<4;j++){
			printf("%.1f",mat[i][j]);
			printf("¥t");
		}
		printf("¥n");
	}
}

/*メイン関数*/
void main()
{
	float Amat[4][4];
	char filename1[]="Amat.txt";
	
	read_matrix(filename1,Amat);
	
	print_matrix(Amat);

}

(4)ファイルから4×4の2次元行列A,Bを読み込み行列の乗算A・B=Cを行い、計算結果Cをファイルに出力するプログラムを作成せよ.
行列Aと同様にBも保存する.[Bmat.txt],


#include<stdio.h>
/*4x4の行列をファイルから読み込む関数*/
void read_matrix(char filename[],float mat[4][4])
{
	int i,j;
	FILE *fp;

	fp=fopen(filename,"r");
	if(fp==NULL){
		printf("ファイルがありませんでした.¥n");
		return;
	}
	for(i=0;i<4;i++){
		for(j=0;j<4;j++){
			fscanf(fp,"%f",&mat[i][j]);
		}
	}
	fclose(fp);
}

/*4x4の行列をファイルに書き出す関数*/
void write_matrix(char filename[],float mat[4][4])
{
	int i,j;
	FILE *fp;

	fp=fopen(filename,"w");
	if(fp==NULL){
		printf("ファイルを作れませんでした.¥n");
		return;
	}
	for(i=0;i<4;i++){
		for(j=0;j<4;j++){
			fprintf(fp,"%f",mat[i][j]);
			fprintf(fp,"¥t");
		}
		fprintf(fp,"¥n");
	}
	fclose(fp);
}
/*4x4の行列を表示する関数*/
void print_matrix(float mat[4][4])
{
	int i,j;
	for(i=0;i<4;i++){
		for(j=0;j<4;j++){
			printf("%.1f",mat[i][j]);
			printf("¥t");
		}
		printf("¥n");
	}
	
	printf("¥n");
}

/*行列の掛け算を行う関数*/
void multi_matrix(float Amat[4][4],float Bmat[4][4],float Cmat[4][4])
{
	int i,j;
	for(i=0;i<4;i++){
		for(j=0;j<4;j++){
			Cmat[i][j]=Amat[i][j]*Bmat[j][i];
		}
	}
}

/*main関数*/
void main()
{
	float Amat[4][4],Bmat[4][4],Cmat[4][4];
	char filename1[]="Amat.txt";
	char filename2[]="Bmat.txt";
	char filename3[]="Cmat.txt";

	read_matrix(filename1,Amat);
	read_matrix(filename2,Bmat);
	
	print_matrix(Amat);
	print_matrix(Bmat);

	multi_matrix(Amat,Bmat,Cmat);

	print_matrix(Cmat);

	write_matrix(filename3,Cmat);
}

(5)前回の課題(4)の文字列の長さを計算する関数を用いて、文字列の前後を反転させる関数を作成せよ.


#include <stdio.h>

/*文字の長さを数える関数*/
int moji_nagasa(char str[])	
{
	………

}

/*文字を入れ替える関数*/
void moji_irekae(char str[], int n)
{
	………
}

/*メイン関数*/
void main()
{
	int n;
	char str[128];

	printf("文字列を入力してください:");
	scanf("%s", str);

	printf("入力された文字列は,%sです.", str);
	printf("文字数は,%dです.", n = moji_nagasa(str));
	
	moji_irekae(str,n);
	
	printf("入れ替えた文字列は,%sです.", str);

}

#include <stdio.h>
int moji_nagasa(char *str)	
{
	int count=0,i;
	
	for( i=0; str[i]!=0; i++ ){
		count++;
	}
	
	return count;

}

void moji_irekae(char *str, int n)
{
	int i;
	char s;
	
	for(i=0; i<n-i; i++){
		s = *( str + (n-1-i) );
		*( str + (n-1-i) ) = *( str + i );
		*( str + i ) = s;
		}
		
	return;
}

void main()
{
	int n;
	
	char str[128];

	printf("文字列を入力してください:");
	scanf("%s", str);

	printf("入力された文字列は,%sです.¥n", str);
	printf("文字数は,%dです.", n = moji_nagasa(str));
	
	moji_irekae(str,n);
	
	printf("入れ替えた文字列は,%sです.¥n", str);

}