C言語で行列を取り扱うにはどうしたらいいのですか?
二次元配列というのは行列の演算のことなのですか?
初心者なのでよく分からないのでなるべく丁寧に教えてもらえるとうれしいのですが。よろしくお願いします。

このQ&Aに関連する最新のQ&A

A 回答 (2件)

参考URLの行列の所と、



http://www.math.meiji.ac.jp/~mk/lecture/ouyousuu …

を参考にしてみて下さい。

参考URL:http://www.pp.iij4u.or.jp/~nabe/c/faq.html
    • good
    • 0

配列の使い方について説明もできますが、このスペースでは無理かもしれません。

たとえば、したのURLには、マトリクス演算のテンプレートのソースコードというかヘッダーとサンプルがあります。残念ながら英語で、CではなくC++です。もしC++が出来るのであれば、たとえばこういった演算ライブラリをそのまま利用するのも手です。Cのマトリクス演算のソースも探せばあると思います。自分で演算するのが課題ではない場合は、あちこち探してみるのも良いと思います。探す先についてはあまりくわしくありませんが、このソースはwww.shareware.comで探しました。

参考URL:http://www.zdnet.com/downloads/stories/info/0,,6 …
    • good
    • 0

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!

このQ&Aを見た人が検索しているワード

このQ&Aと関連する良く見られている質問

QC言語の行列演算に関する質問

これが私のプログラムです。

##############################################
#include<stdio.h>

int main(void)
{
int i, j, k, c;
int matrix1[4][3];  /*4かけ3行列*/
int matrix2[3][4];   /*3かけ4行列*/
int matrix[4][4]; /* matrix1とmatrix2の掛け算*/

puts("4掛け3行列の入力:");
for(i=0; i<4; i++) {
for(j=0; j<3; j++) {
printf("matrix1[%d][%d]=", i+1, j+1);
scanf("%d", &matrix1[i][j]);
}
putchar('\n');
}

putchar('\n');
puts("3掛け4行列の入力:");
for(i=0; i<3; i++) {
for(j=0; j<4; j++) {
printf("matrix2[%d][%d]=", i+1, j+1);
scanf("%d", &matrix1[i][j]);
}
putchar('\n');
}


putchar('\n');
puts("行列の積:");
for(i=0; i<4; i++) {
for(j=0; j<4; j++) {
c = 0;
for(k=0; k<3; k++)
c = c + matrix1[i][k]*matrix2[k][j];
c = matrix[i][j];
printf("%4d", matrix[i][j]);
}
putchar('\n');
}

putchar('\n');
puts("4掛け4行列の計算結果:");
for(i=0; i<5; i++) {
for(j=0; j<5; j++)
printf("%4d", matrix[i][j]);
putchar('\n');
}




return 0;
}
##############################################



これを実行すると、
##############################################
4掛け3行列の入力:
matrix1[1][1]=1
matrix1[1][2]=1
matrix1[1][3]=1

matrix1[2][1]=1
matrix1[2][2]=1
matrix1[2][3]=1

matrix1[3][1]=1
matrix1[3][2]=1
matrix1[3][3]=1

matrix1[4][1]=1
matrix1[4][2]=1
matrix1[4][3]=1


3掛け4行列の入力:
matrix2[1][1]=1
matrix2[1][2]=1
matrix2[1][3]=1
matrix2[1][4]=1

matrix2[2][1]=1
matrix2[2][2]=11
matrix2[2][3]=1
matrix2[2][4]=1

matrix2[3][1]=1
matrix2[3][2]=1
matrix2[3][3]=1
matrix2[3][4]=1


行列の積:
1835627636160006154118698333341952802655
1 04196909 0
0 0 0 0
4196832 04195728 0

4掛け4行列の計算結果:
1835627636160006154118698333341952802655 1
1 04196909 0 0
0 0 0 04196832
4196832 04195728 01673351312
1673351312327656176885764550097164196832
##############################################

となってしまいます。どのように改善すればようでしょうか?

これが私のプログラムです。

##############################################
#include<stdio.h>

int main(void)
{
int i, j, k, c;
int matrix1[4][3];  /*4かけ3行列*/
int matrix2[3][4];   /*3かけ4行列*/
int matrix[4][4]; /* matrix1とmatrix2の掛け算*/

puts("4掛け3行列の入力:");
for(i=0; i<4; i++) {
for(j=0; j<3; j++) {
printf("matrix1[%d][%d]=", i+1, j+1);
scanf("%d", &matri...続きを読む

Aベストアンサー

以下のようにしてください。修正個所は//修正のコメントをいれてます。
-------------------------------
#include<stdio.h>

int main(void)
{
int i, j, k, c;
int matrix1[4][3]; /*4かけ3行列*/
int matrix2[3][4]; /*3かけ4行列*/
int matrix[4][4]; /* matrix1とmatrix2の掛け算*/

puts("4掛け3行列の入力:");
for(i=0; i<4; i++) {
for(j=0; j<3; j++) {
printf("matrix1[%d][%d]=", i+1, j+1);
scanf("%d", &matrix1[i][j]);
}
putchar('\n');
}

putchar('\n');
puts("3掛け4行列の入力:");
for(i=0; i<3; i++) {
for(j=0; j<4; j++) {
printf("matrix2[%d][%d]=", i+1, j+1);
scanf("%d", &matrix2[i][j]); //修正matrix1->matrix2
}
putchar('\n');
}


putchar('\n');
puts("行列の積:");
for(i=0; i<4; i++) {
for(j=0; j<4; j++) {
c = 0;
for(k=0; k<3; k++)
c = c + matrix1[i][k]*matrix2[k][j];
matrix[i][j]=c; //修正 右辺と左辺を交換
printf("%4d", matrix[i][j]);
}
putchar('\n');
}

putchar('\n');
puts("4掛け4行列の計算結果:");
for(i=0; i<4; i++) { //修正 5->4
for(j=0; j<4; j++) //修正 5->4
printf("%4d", matrix[i][j]);
putchar('\n');
}

return 0;
}
--------------------------------------
以下、実行結果です。
ケース1
4掛け3行列の入力:
matrix1[1][1]=1
matrix1[1][2]=1
matrix1[1][3]=1

matrix1[2][1]=1
matrix1[2][2]=1
matrix1[2][3]=1

matrix1[3][1]=1
matrix1[3][2]=1
matrix1[3][3]=1

matrix1[4][1]=1
matrix1[4][2]=1
matrix1[4][3]=1


3掛け4行列の入力:
matrix2[1][1]=1
matrix2[1][2]=1
matrix2[1][3]=1
matrix2[1][4]=1

matrix2[2][1]=1
matrix2[2][2]=1
matrix2[2][3]=1
matrix2[2][4]=1

matrix2[3][1]=1
matrix2[3][2]=1
matrix2[3][3]=1
matrix2[3][4]=1


行列の積:
3 3 3 3
3 3 3 3
3 3 3 3
3 3 3 3

4掛け4行列の計算結果:
3 3 3 3
3 3 3 3
3 3 3 3
3 3 3 3

ケース2
4掛け3行列の入力:
matrix1[1][1]=1
matrix1[1][2]=2
matrix1[1][3]=3

matrix1[2][1]=4
matrix1[2][2]=5
matrix1[2][3]=6

matrix1[3][1]=7
matrix1[3][2]=8
matrix1[3][3]=9

matrix1[4][1]=10
matrix1[4][2]=11
matrix1[4][3]=12


3掛け4行列の入力:
matrix2[1][1]=13
matrix2[1][2]=14
matrix2[1][3]=15
matrix2[1][4]=16

matrix2[2][1]=17
matrix2[2][2]=18
matrix2[2][3]=19
matrix2[2][4]=20

matrix2[3][1]=21
matrix2[3][2]=22
matrix2[3][3]=23
matrix2[3][4]=24


行列の積:
110 116 122 128
263 278 293 308
416 440 464 488
569 602 635 668

4掛け4行列の計算結果:
110 116 122 128
263 278 293 308
416 440 464 488
569 602 635 668

以下のようにしてください。修正個所は//修正のコメントをいれてます。
-------------------------------
#include<stdio.h>

int main(void)
{
int i, j, k, c;
int matrix1[4][3]; /*4かけ3行列*/
int matrix2[3][4]; /*3かけ4行列*/
int matrix[4][4]; /* matrix1とmatrix2の掛け算*/

puts("4掛け3行列の入力:");
for(i=0; i<4; i++) {
for(j=0; j<3; j++) {
printf("matrix1[%d][%d]=", i+1, j+1);
scanf("%d", &matrix1[i][j]);
}
putchar('\n');
}

putchar('\n');
puts("3掛け4行列の入力:");
for(i...続きを読む

QC言語の二次元配列について教えて下さい。

二次元配列で、次の行列の1の要素の添え字を書き出したいです。例えばa11の場合、(0,0)の様にしたいです。

{1,0,1,0}
{0,1,1,1}
  {1,0,0,1}

自分で出来る範囲で組み上げたプログラムを載せます。

#include <stdio.h>
int main(void)
{
int x,y;
int a[3][4]=
{{1,0,1,0},
{0,1,1,1},
{1,0,0,1}};
for(x=0;x<3;x++){
for(y=0;y<4;y++){
printf("%3d",a[x][y]);
}
}
return (0);
}

実行結果
(0,0) (0,2) (1,1) (1,2) (1,3) (2,0) (2,3)

あくまで上の実行結果を出力するものを組み上げたいのですが、続きがさっぱり解りません。それと上記のプログラムには何らかの間違いがあるかもしれません。どなたか解る方、出来るだけ簡単なプログラムを教えて下さい。宜しくお願います。

二次元配列で、次の行列の1の要素の添え字を書き出したいです。例えばa11の場合、(0,0)の様にしたいです。

{1,0,1,0}
{0,1,1,1}
  {1,0,0,1}

自分で出来る範囲で組み上げたプログラムを載せます。

#include <stdio.h>
int main(void)
{
int x,y;
int a[3][4]=
{{1,0,1,0},
{0,1,1,1},
{1,0,0,1}};
for(x=0;x<3;x++){
for(y=0;y<4;y++){
printf("%3d",a[x][y]);
}
}
return (0);
}

実行結果
(0,0) (0,2) (1,1) (1,2) (1,3) (2,0) (2...続きを読む

Aベストアンサー

a[x][y] == 1 のときだけ printf(...) すればいいんでしょ?
printf(...) を if でくるめば完成。

Q3次元配列から2次元配列への代入

C言語初心者です。
詳しい方、宜しくお願い致します。

下記のような三次元配列(Sanjigen[2][5][5])があります。
ダンプしたもので見難くてすみません。
00FFBCBC [0][0][0] 01 02 03 04 05
00FFBCC1 [0][1][0] 06 07 08 09 10
00FFBCC6 [0][2][0] 11 12 13 14 15
00FFBCCB [0][3][0] 16 17 18 19 20
00FFBCD0 [0][4][0] 21 22 23 24 25
00FFBCE4 [1][0][0] 26 27 28 29 30
00FFBCE9 [1][1][0] 31 32 33 34 35
00FFBCEE [1][2][0] 36 37 38 39 40
00FFBCF3 [1][3][0] 41 42 43 44 45
00FFBCF8 [1][4][0] 46 47 48 49 50

このデータ(Sanjigen[2][5][5])を、二次元配列にしまう方法をご教授ください。
Nijigen1[5][5]には三次元配列のデータ(1~25)と(26~50)をアンドしたデータを格納します。
Nijigen2[5][5]には三次元配列のデータ(1~25)と(26~50)をオアしたデータを格納します。
下記は自分の作ったプログラムですが、うまくいきません。

charSanjigen[2][5][5];
charNijigen1[5][5];
charNijigen2[5][5];

void get_data( void )
{
char i;

for( i=0; i<8; ++i ){
Nijigen1[i] = Sanjigen[0][i] & Sanjigen[1][i];
Nijigen2[i] = Sanjigen[0][i] ^ Sanjigen[1][i];
}
}

説明わかりにくくて申し訳ありません。
宜しくお願い致します。

C言語初心者です。
詳しい方、宜しくお願い致します。

下記のような三次元配列(Sanjigen[2][5][5])があります。
ダンプしたもので見難くてすみません。
00FFBCBC [0][0][0] 01 02 03 04 05
00FFBCC1 [0][1][0] 06 07 08 09 10
00FFBCC6 [0][2][0] 11 12 13 14 15
00FFBCCB [0][3][0] 16 17 18 19 20
00FFBCD0 [0][4][0] 21 22 23 24 25
00FFBCE4 [1][0][0] 26 27 28 29 30
00FFBCE9 [1][1][0] 31 32 33 34 35
00FFBCEE [1][2][0] 36 37 38 39 40
00FFBCF3 [1][3][0] 41 42 43 44 ...続きを読む

Aベストアンサー

>同じような処理を何回もしなければいけないので、できれば1つのループにしたいんです。

配列が「ダンプした通りのメモリ配置」になっているとの保証があるなら、以下のようにすればよい。

char Sanjigen[2][5][5];
char Nijigen1[5][5];
char Nijigen2[5][5];

void get_data( void )
{
int i;
char *p1 = &Sanjigen[0][0][0];
char *p2 = &Sanjigen[1][0][0];
char *p3 = &Nijigen1[0][0];
char *p4 = &Nijigen2[0][0];

for(i=0;i < 5 * 5; ++i,p1++,p2++,p3++,p4++ ){
*p3 = *p1 & *p2;
*p4 = *p1 | *p2;
}
}

もし「ダンプした通りのメモリ配置」になってないなら、正しく動く保証はない。

QVBからDLLへ多次元配列を渡す/配列の添え字

C++で作ったdllにVBAから配列を渡して、計算結果を再びVBAに戻して、アウトプットはVBAで、ということをしています。(経験豊富な方への相談です。)

具体的には、渡したい配列の先頭アドレスをlong型で記憶し、そのlong型の配列を受け渡ししています。
ただ、ご存知の方が多いかもしれませんが、VBAとC++では配列の添え字の順序が逆になっており、非常に面倒です。どういうことかといいますと、
Dim array(0 to 4, 0 to 9) as long
をdllに渡し、array(2,6)を参照したい場合、C++では(Cでの配列名をc_arrayとし、これに先頭アドレスを入れると)、
c_array[(4+1)*6 + 2 ];
としなければならないと思います。これをプリプロセッサで
#define C_ARRAY(a,b) c_array[(4+1)*b + a]
としたらVBでの配列の感覚で扱えますが、この擬似配列C_ARRAY(a,b)を関数に渡すときなどは結局同じ混乱が再び生じることになってしまいます。

これを、何らかの方法で、簡潔に解決することはできないものでしょうか?
VBA(エクセルを念頭においています)のほうで配列の添え字の順序をC++のそれに沿うように変更できたりしたら非常にうれしいですが、無理でしょうか?

C++で作ったdllにVBAから配列を渡して、計算結果を再びVBAに戻して、アウトプットはVBAで、ということをしています。(経験豊富な方への相談です。)

具体的には、渡したい配列の先頭アドレスをlong型で記憶し、そのlong型の配列を受け渡ししています。
ただ、ご存知の方が多いかもしれませんが、VBAとC++では配列の添え字の順序が逆になっており、非常に面倒です。どういうことかといいますと、
Dim array(0 to 4, 0 to 9) as long
をdllに渡し、array(2,6)を参照したい場合、C++では(Cでの配列名をc_array...続きを読む

Aベストアンサー

SAFEARRAYを使用してマーシャリングを行うという方法があります。
http://www.microsoft.com/japan/msdn/vs_previous/vbasic/docs/dll/#8

Q二次元配列による文字列の配列の受渡しについての質問です。

二次元配列による文字列の配列の受渡しについての質問です。

#include <stdio.h>

void print_pname(char str[][5], int n)
{
int i, j;
for (i = 0; i < n; i++)
{
printf("str[%d] = \"", i);
for (j = 0; str[i][j] != '\0'; j++)
putchar(str[i][j]);
printf("\"\n");
}
}

int main(void)
{
char ary[][5] = {"Lisp", "C", "Ada"};

print_pname(ary, sizeof(ary) / sizeof(ary[0]));
return 0;
}

上のプログラム中の関数print_pnameの引数char str[][5]についてですが
char (*str)[5](配列のポインタ)と変更した場合にwarningが多数発生します。
これはどうしてでしょうか?
また、上のプログラムを配列のポインタを使って変更することは可能でしょうか?

以上、よろしくお願いします。

二次元配列による文字列の配列の受渡しについての質問です。

#include <stdio.h>

void print_pname(char str[][5], int n)
{
int i, j;
for (i = 0; i < n; i++)
{
printf("str[%d] = \"", i);
for (j = 0; str[i][j] != '\0'; j++)
putchar(str[i][j]);
printf("\"\n");
}
}

int main(void)
{
char ary[][5] = {"Lisp", "C", "Ada"};

print_pname(ary, sizeof(ary) / sizeof(ary[0]));
return 0;
}

上のプログラム中の関数print_pnameの引数char str[][5]についてですが
char (*st...続きを読む

Aベストアンサー

いや, 確かにそこはおかしいけど (注: どっちにしても未定義動作ですがそこはスルーしてた), while の条件が変です>#6. このまままわると *ary[3] を参照しちゃいます.
で本題に戻ると,
char (*ary)[5] = {"Lisp", "C", "Ada"};
は ary を「『大きさ 5 の配列』へのポインタ」として定義しています. ポインタはスカラーですから, このように複数の値を使って初期化することはできません.
なお, GCC (や ISO C に従っている処理系) なら
char (*ary)[5] = (char [][5]){"Lisp", "C", "Ada"};
で初期化できるかもしれません. でも, そのあとがどうせダメか.


人気Q&Aランキング

おすすめ情報