🎄teratailクリスマスプレゼントキャンペーン2024🎄』開催中!

\teratail特別グッズやAmazonギフトカード最大2,000円分が当たる!/

詳細はこちら
C

C言語は、1972年にAT&Tベル研究所の、デニス・リッチーが主体となって作成したプログラミング言語です。 B言語の後継言語として開発されたことからC言語と命名。そのため、表記法などはB言語やALGOLに近いとされています。 Cの拡張版であるC++言語とともに、現在世界中でもっとも普及されているプログラミング言語です。

プログラミング言語

プログラミング言語はパソコン上で実行することができるソースコードを記述する為に扱う言語の総称です。

Q&A

1回答

967閲覧

fuzzy c-means法で望んだ値が出ない

ro_tose

総合スコア8

C

C言語は、1972年にAT&Tベル研究所の、デニス・リッチーが主体となって作成したプログラミング言語です。 B言語の後継言語として開発されたことからC言語と命名。そのため、表記法などはB言語やALGOLに近いとされています。 Cの拡張版であるC++言語とともに、現在世界中でもっとも普及されているプログラミング言語です。

プログラミング言語

プログラミング言語はパソコン上で実行することができるソースコードを記述する為に扱う言語の総称です。

0グッド

1クリップ

投稿2019/12/24 02:40

編集2019/12/24 06:05

前提・実現したいこと

C言語でfuzzy c-means法を作りたいのですが、プログラム結果望んだ値がでません
最後の出力結果、tes,で、3つのクラスタの帰属度の合計が1になると思うんですがnanがでます。

発生している問題・エラーメッセージ

計算式がどこかおかしいのか、おそらく帰属度を求める段階でおかしい数値がでている

エラーメッセージ

該当のソースコード

C言語

1#include <stdio.h> 2#include <stdlib.h> 3#include <string.h> 4#include <math.h> 5#include <time.h> 6#include <unistd.h> 7 8#include "MT.h" 9 10#define c 3 11#define N_CITY 51 12#define TSPFILE "eil51.tsp" 13 14double sm; 15int distance[c][N_CITY]; //距離 16 17 int x[N_CITY]; 18 int y[N_CITY]; //座標 19 20struct cluster{ 21 double now_x[N_CITY]; 22 double now_y[N_CITY]; //座標 23 int no; 24 double new_x; 25 double new_y; 26 double uj[N_CITY]; 27 double sm_uj; 28}; 29 30int n=N_CITY; //都市数 31int z[N_CITY]; //都市番号 32 33 34 35 36int belongs[N_CITY]; //クラスタの所属 37struct cluster center[c]; 38 39 40void read_tsp_file(char *tsp_file) 41 { 42 FILE* fp; 43 char buf[100]; 44 int i, j; 45 int n; 46 47 fp = fopen(tsp_file, "r"); 48 if (fp == NULL) 49 { 50 fprintf(stderr,"No instance file specified, abort\n"); 51 exit(1); 52 } 53 printf("Reading tsp-file %s ... \n\n", tsp_file); 54 55 56 57 for (i = 0; i < N_CITY; i++) 58 { 59 fscanf(fp,"%d %d %d", &z[i], &x[i], &y[i]); 60 } 61 fclose(fp); 62} 63 64double dis(double cenx,double ceny,int x,int y) 65{ 66 67 double xd =x-cenx; 68 double yd =y-ceny; 69 double d = sqrt(xd * xd + yd * yd); 70 return d; 71} 72 73int main(void){ 74 int i,j,k; 75 char tsp_file[]=TSPFILE; 76 int rnd; 77 double av_dis=0.0; 78 int loop; 79 int start; 80 double maer; 81 double kari[c]; 82 83 printf("スタート都市"); 84 scanf("%d",&start); 85 /* ファイルを読み込む */ 86 read_tsp_file(tsp_file); 87 88 89 maer=1.1; 90 91 init_genrand((unsigned)time(NULL)); 92 for(i=0;i<c;i++){ 93 for(j=0;j<n;j++){ 94 center[i].uj[j]=genrand_real1(); 95 96 } 97 } 98 loop=0; 99 100 while( 101 /*((center[i].x[0]-center[i-1]x[0])&&(center[i].y[0]-center[i-1].y[0]))&& 102 ((center[i].x[1]-center[i-1]x[1])&&(center[i].y[1]-center[i-1].y[1]))&& 103 ((center[i].x[2]-center[i-1]x[2])&&(center[i].y[2]-center[i-1].y[2]))|| 104 */ 105 loop<10){ 106 for(j=0;j<c;j++){ 107 center[j].new_x=0.0; 108 center[j].new_y=0.0; 109 center[j].sm_uj=0.0; 110 center[j].no=0; 111 center[j].uj[start]=1.0; 112 kari[j]=0.0; 113 } 114 115 116 /*中心との 距離を計算する */ 117 for(i=0;i<c;i++){ 118 for(j=0;j<n;j++){ 119 120 center[i].new_x+=pow(center[i].uj[j],maer)*x[j]; 121 center[i].new_y+=pow(center[i].uj[j],maer)*y[j]; 122 center[i].sm_uj+=pow(center[i].uj[j],maer); 123 } 124 125 center[i].new_x/=center[i].sm_uj; 126 center[i].new_y/=center[i].sm_uj; 127 } 128 129 for(i=0;i<c;i++){ 130 for(j=0;j<n;j++){ 131 if(j!=start){ 132 for(k=0;k<c;k++){ 133 kari[i]=pow(dis(center[i].new_x,center[i].new_y,x[j],y[j]),2.0)/pow(dis(center[k].new_x,center[k].new_y,x[j],y[j]),2.0); 134 center[i].uj[j]+=pow(kari[i],1/(maer-1)); 135 } 136 center[i].uj[j]=pow(center[i].uj[j],-1.0); 137 } 138 else{}; 139 } 140 } 141 loop++; 142 } 143 sm=0; 144 sm=center[0].uj[0]+center[1].uj[0]+center[2].uj[0]; 145 printf("test%f\n",sm); 146 printf("クラスタ−1\n"); 147 printf("中心点:%f %f\n",center[0].new_x,center[0].new_y); 148 for(i=0;i<n;i++){ 149 printf("帰属度:%d %f\n",i,center[0].uj[i]); 150 151 } 152 153 printf("クラスター2\n"); 154 printf("都市数:%d\n",center[1].no); 155 printf("中心点:%f %f\n",center[1].new_x,center[1].new_y); 156 for(i=0;i<n;i++){ 157 printf("帰属度:%d %f\n",i,center[1].uj[i]); 158 159 } 160 161 printf("クラスター3\n"); 162 printf("都市数:%d\n",center[2].no); 163 printf("中心点:%f %f\n",center[2].new_x,center[2].new_y); 164 for(i=0;i<n;i++){ 165 printf("帰属度:%d %f",i,center[2].uj[i]); 166 167 } 168 169} 170
読み込む都市コード eil51.tsp 1 37 52 2 49 49 3 52 64 4 20 26 5 40 30 6 21 47 7 17 63 8 31 62 9 52 33 10 51 21 11 42 41 12 31 32 13 5 25 14 12 42 15 36 16 16 52 41 17 27 23 18 17 33 19 13 13 20 57 58 21 62 42 22 42 57 23 16 57 24 8 52 25 7 38 26 27 68 27 30 48 28 43 67 29 58 48 30 58 27 31 37 69 32 38 46 33 46 10 34 61 33 35 62 63 36 63 69 37 32 22 38 45 35 39 59 15 40 5 6 41 10 17 42 21 10 43 5 64 44 30 15 45 39 10 46 32 39 47 25 32 48 25 55 49 48 28 50 56 37 51 30 40 EOF

試したこと

ウィキや、いろいろなサイトの式を読んでいくつか修正しましたが望んだ値を得ることができませんでした。

スタート都市9 Reading tsp-file eil51.tsp ... test-nan クラスタ−1 中心点:52.621189 30.597594 帰属度:0 0.000000 帰属度:1 0.003076 帰属度:2 0.000022 帰属度:3 0.000000 帰属度:4 0.617786 帰属度:5 0.000000 帰属度:6 0.000000 帰属度:7 0.000000 帰属度:8 0.618009 帰属度:9 1.000000 帰属度:10 0.203836 帰属度:11 0.000013 帰属度:12 0.000000 帰属度:13 0.000005 帰属度:14 0.000129 帰属度:15 0.618023 帰属度:16 0.000000 帰属度:17 0.000000 帰属度:18 0.000000 帰属度:19 0.007880 帰属度:20 0.618012 帰属度:21 0.000000 帰属度:22 0.000000 帰属度:23 0.000011 帰属度:24 0.000001 帰属度:25 0.000000 帰属度:26 0.000000 帰属度:27 0.000000 帰属度:28 0.614753 帰属度:29 0.618064 帰属度:30 0.000000 帰属度:31 0.000000 帰属度:32 0.607877 帰属度:33 0.618068 帰属度:34 0.023109 帰属度:35 0.008968 帰属度:36 0.000000 帰属度:37 0.618057 帰属度:38 0.618057 帰属度:39 0.000000 帰属度:40 0.000000 帰属度:41 0.000000 帰属度:42 0.000010 帰属度:43 0.000000 帰属度:44 0.012702 帰属度:45 0.000410 帰属度:46 0.000000 帰属度:47 0.000000 帰属度:48 0.618052 帰属度:49 0.618059 帰属度:50 0.000043 クラスター2 都市数:0 中心点:23.588639 22.377194 帰属度:0 0.000000 帰属度:1 0.000000 帰属度:2 0.000000 帰属度:3 0.618072 帰属度:4 0.000956 帰属度:5 0.000237 帰属度:6 0.000002 帰属度:7 0.000000 帰属度:8 0.000000 帰属度:9 1.000000 帰属度:10 0.000003 帰属度:11 0.618087 帰属度:12 0.618074 帰属度:13 0.602663 帰属度:14 0.618301 帰属度:15 0.000000 帰属度:16 0.618112 帰属度:17 0.618072 帰属度:18 0.618061 帰属度:19 0.000000 帰属度:20 0.000000 帰属度:21 0.000000 帰属度:22 0.000015 帰属度:23 0.025906 帰属度:24 0.617802 帰属度:25 0.000000 帰属度:26 0.000000 帰属度:27 0.000000 帰属度:28 0.000000 帰属度:29 0.000000 帰属度:30 0.000000 帰属度:31 0.000000 帰属度:32 0.035648 帰属度:33 0.000000 帰属度:34 0.000001 帰属度:35 0.000002 帰属度:36 0.618102 帰属度:37 0.000000 帰属度:38 0.000000 帰属度:39 0.618045 帰属度:40 0.618063 帰属度:41 0.618032 帰属度:42 0.001305 帰属度:43 0.617944 帰属度:44 0.613916 帰属度:45 0.013335 帰属度:46 0.618065 帰属度:47 0.000000 帰属度:48 0.000000 帰属度:49 0.000000 帰属度:50 0.008043 クラスター3 都市数:0 中心点:35.803278 53.433737 帰属度:0 0.618037 帰属度:1 0.617188 帰属度:2 0.618027 帰属度:3 0.000000 帰属度:4 0.000005 帰属度:5 0.617990 帰属度:6 0.618047 帰属度:7 0.618040 帰属度:8 0.000000 帰属度:9 1.000000 帰属度:10 0.549284 帰属度:11 0.000010 帰属度:12 0.000000 帰属度:13 0.052614 帰属度:14 0.000000 帰属度:15 0.000002 帰属度:16 0.000000 帰属度:17 0.000000 帰属度:18 0.000000 帰属度:19 0.615860 帰属度:20 0.000003 帰属度:21 0.618045 帰属度:22 0.618044 帰属度:23 0.610755 帰属度:24 0.000841 帰属度:25 0.618022 帰属度:26 0.618051 帰属度:27 0.618058 帰属度:28 0.011801 帰属度:29 0.000000 帰属度:30 0.618048 帰属度:31 0.618052 帰属度:32 0.000001 帰属度:33 0.000000 帰属度:34 0.611532 帰属度:35 0.615556 帰属度:36 0.000000 帰属度:37 0.000000 帰属度:38 0.000000 帰属度:39 0.000000 帰属度:40 0.000000 帰属度:41 0.000000 帰属度:42 0.617676 帰属度:43 0.000000 帰属度:44 0.000000 帰属度:45 0.614108 帰属度:46 0.000000 帰属度:47 0.618043 帰属度:48 0.000000 帰属度:49 0.000000 帰属度:50 0.615774

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

y_waiwai

2019/12/24 03:25

提示のコードではどういう結果が出るんでしょうか
ro_tose

2019/12/24 03:52

追加させていただきました。
guest

回答1

0

C

1#include <stdio.h> 2 3/* 中略 */ 4 5int sm; // int型 6 7/* 中略 */ 8 9 10int main(void){ 11/* 中略 */ 12 printf("test%f\n",sm); // %f なのに int型 13/* 中略 */ 14 15}

クラスタの中心を計算したあと所属度を更新しますが、
足し合わせる際に0で初期化してないので妙な値になってるはずです。


  • インデントをちゃんと揃えましょう。読みづらくなってバグのもとになります。
  • 無意味にグローバル変数を使うのをやめましょう。読みづらくなってバグのもとになります。
  • 関数の冒頭に変数を宣言するのをやめて、使う直前に宣言しましょう。読みづらくなってバグのもとになります。
  • 可能ならC言語を使うのをやめましょう。

2016年、C言語はどう書くべきか (前編)

C言語の第1のルールは、「もし避けられるならC言語を使うな」ということです。

投稿2019/12/24 03:58

編集2019/12/24 07:41
ozwk

総合スコア13551

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

ro_tose

2019/12/24 04:05

そこ見落としていました・・・ただ修正したところ値は出たのですが、testは0.617994となったので他にも問題があるように思えます。 合計は1になるはずだと思うので・・・
ozwk

2019/12/24 05:37

double d = sqrt(xd * xd + yd * yd)+0.5; この0.5はなんですか?
ro_tose

2019/12/24 06:06

別のシステムで使用した距離を求める関数を修正して使っていたのですがそこを修正し忘れていました。 必要がない数値なので修正しました。
ro_tose

2019/12/24 06:08

他のC言語に使用したプログラムに組み込みたいと考えているのでできればC言語で作成したいですがダメなら他の言語で作成することも視野に入れようと思います。
ozwk

2019/12/24 06:37 編集

私は fuzzy c-means を今日知ったので今調べています。 start なる値がありますが、これは fuzzy c-meansに出てくる概念ですか? (都市数だのTSPだのから察するにこれ巡回セールスマン問題のプログラム無理やり改造してません?)
ro_tose

2019/12/24 06:38

解答のために調べていただいてありがとうございます。 このスタートなんですけど、このあと分けた都市で経路を作る際、共通の出発点がほしいので、そのためにすべての都市に帰属度1.0を持った都市を作りたいと思っているので設定しています。
ozwk

2019/12/24 06:47

そういう小細工をするのはまず普通のを作ってからにしましょう
ro_tose

2019/12/24 07:10

了解です
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

まだベストアンサーが選ばれていません

会員登録して回答してみよう

アカウントをお持ちの方は

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.36%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問