C言語なら俺に聞け! Part 71

このエントリーをはてなブックマークに追加
1v(^o^i)d
まず問題を冷静に吟味してCの話か否かをはっきりさせてから質問しましょう。
質問する前には最低限検索を。

GUIなどの標準Cではできない事の質問は使用している開発環境のスレへGo! (←ここ注目)
ソース丸投げ、宿題、書籍 は専門の別スレがあるのでそこへさようなら。

コンパイラを探しているなら >>2-13 を。
上記を逸した場合の結果は激しく未定義だYO!

C FAQ 日本語訳
http://www.catnet.ne.jp/kouno/c_faq/c_faq.html
Cプログラマ必読 ・プログラミング言語C(通称 K&R)
http://www.amazon.co.jp/exec/obidos/ASIN/4320026926/

各種リンクは>>3-20あたり(誰か適当に貼って)

C言語なら俺に聞け! Part 70
http://pc2.2ch.net/test/read.cgi/tech/1072212403/
【コンパイラ】
gcc
http://gcc.gnu.org/

【Win32用の開発環境のみ。】
gcc-cygwin
http://www.redhat.com/software/tools/cygwin/
gcc-mingw
http://www.mingw.org
Digital Mars C++
http://www.digitalmars.com/
Open Watcom
http://www.openwatcom.com/
Borland C++ Compiler 5.5.1
http://www.borland.co.jp/cppbuilder/freecompiler/

【ライセンスや機能などに問題あり】
Microsot C/C++ 13.0.9466(VC.NET)
http://www.microsoft.com/japan/msdn/netframework/downloads/
LCC-Win32
http://www.cs.virginia.edu/~lcc-win32/
CINT
http://root.cern.ch/root/Cint.html
めじろ++98
http://www.vector.co.jp/soft/win95/prog/se075910.html
Intel C++ Compiler for Linux
http://developer.intel.com/software/products/compilers/clin/noncom.htm
乙のすけ。
っていうか、IDEも乗せろよ アホ助

http://www.widestudio.org/
C言語なら俺に聞け part70
http://pc2.2ch.net/test/read.cgi/tech/1072212403/
69 http://pc2.2ch.net/tech/kako/1070/10708/1070896646.html
68 http://pc2.2ch.net/tech/kako/1069/10695/1069552879.html
67 http://pc2.2ch.net/tech/kako/1068/10684/1068464309.html
66 http://pc2.2ch.net/tech/kako/1066/10665/1066560665.html
65 http://pc2.2ch.net/tech/kako/1064/10642/1064234533.html
64 http://pc2.2ch.net/tech/kako/1061/10617/1061779941.html
63 http://pc2.2ch.net/tech/kako/1060/10600/1060085935.html
62 http://pc2.2ch.net/tech/kako/1058/10587/1058754682.html
61 http://pc2.2ch.net/tech/kako/1057/10576/1057677056.html
60 http://pc2.2ch.net/tech/kako/1056/10568/1056806789.html
59 http://pc2.2ch.net/tech/kako/1056/10561/1056109884.html
58 http://pc2.2ch.net/tech/kako/1054/10549/1054906871.html
57 http://pc2.2ch.net/tech/kako/1053/10537/1053725121.html
56 http://pc2.2ch.net/tech/kako/1052/10525/1052542761.html
55 http://pc2.2ch.net/tech/kako/1051/10515/1051528386.html
54 http://pc2.2ch.net/tech/kako/1049/10499/1049968153.html
53 http://pc2.2ch.net/tech/kako/1048/10489/1048995232.html
52 http://pc2.2ch.net/tech/kako/1047/10472/1047275669.html
51 http://pc2.2ch.net/tech/kako/1046/10461/1046104909.html
50 http://pc2.2ch.net/tech/kako/1044/10449/1044938752.html
49 http://pc2.2ch.net/tech/kako/1042/10426/1042646178.html
49 http://pc2.2ch.net/tech/kako/1042/10426/1042640474.html
48 http://pc3.2ch.net/tech/kako/1041/10411/1041127646.html
47 http://pc3.2ch.net/tech/kako/1040/10400/1040048202.html
46 http://pc3.2ch.net/tech/kako/1039/10393/1039328710.html
45 http://pc3.2ch.net/tech/kako/1038/10384/1038405432.html
6:04/01/15 00:35
44 http://pc3.2ch.net/tech/kako/1037/10377/1037796472.html
43 http://pc3.2ch.net/tech/kako/1037/10372/1037281411.html
43 http://pc3.2ch.net/tech/kako/1037/10371/1037134356.html
42 http://pc3.2ch.net/tech/kako/1037/10371/1037101156.html
41 http://pc3.2ch.net/tech/kako/1036/10368/1036876790.html
40 http://pc3.2ch.net/tech/kako/1036/10366/1036673739.html
39 http://pc3.2ch.net/tech/kako/1036/10364/1036409391.html
38 http://pc3.2ch.net/tech/kako/1035/10357/1035729526.html
37 http://pc3.2ch.net/tech/kako/1035/10356/1035623265.html
36 http://pc3.2ch.net/tech/kako/1035/10352/1035211039.html
35 http://pc3.2ch.net/tech/kako/1034/10343/1034337064.html
34 http://pc3.2ch.net/tech/kako/1033/10332/1033240509.html
33 http://pc3.2ch.net/tech/kako/1032/10326/1032606064.html
32 http://pc3.2ch.net/tech/kako/1031/10319/1031905402.html
31 http://pc3.2ch.net/tech/kako/1031/10313/1031340950.html
30 http://pc3.2ch.net/tech/kako/1030/10307/1030786546.html
29 http://pc3.2ch.net/tech/kako/1029/10296/1029605182.html
28 http://pc3.2ch.net/tech/kako/1028/10284/1028495798.html
27 http://pc3.2ch.net/tech/kako/1027/10271/1027160374.html
26 http://pc.2ch.net/tech/kako/1026/10260/1026048820.html
25 http://pc.2ch.net/tech/kako/1024/10249/1024918442.html
24 http://pc.2ch.net/tech/kako/1024/10240/1024033400.html
23 http://pc.2ch.net/tech/kako/1023/10230/1023024817.html
22 http://pc.2ch.net/tech/kako/1022/10224/1022402165.html
21 http://pc.2ch.net/tech/kako/1022/10220/1022045622.html
20 http://pc.2ch.net/tech/kako/1021/10214/1021459016.html
7:04/01/15 00:36
8:04/01/15 00:37
c++の機能を堪能したいなら
STLスレッド part1
http://pc.2ch.net/tech/kako/1004/10042/1004287394.html
STLスレッド part2
http://pc3.2ch.net/tech/kako/1026/10267/1026793823.html
Generic Programming with C++ Template
http://pc.2ch.net/tech/kako/1008/10085/1008593126.html
【C++】template 統合スレ -- STL/Boost/Loki, etc.
http://pc2.2ch.net/tech/kako/1037/10377/1037795348.html
【C++】template 統合スレ -- Part2
http://pc2.2ch.net/tech/kako/1047/10479/1047978546.html
【C++】template 統合スレ -- Part3
http://pc2.2ch.net/test/read.cgi/tech/1066493064/-100
9デフォルトの名無しさん:04/01/15 04:19
>>1
おつ
10デフォルトの名無しさん:04/01/15 08:14
配列を関数をつかって並び替えるというものを作りたいのですが
例えばまずメインのほうで[0][0],[0][1],[1][0]・・・[4][1]まで読み込んで
それを関数のほうで並びかえて出力したいのですがうまくいかないんです。
上の配列のデータ全てに対して関数を使うやり方がいまいちわかりません。
全てというのは1つ1つに対してという意味ではなく全てを同時にということです。
お願いします。
11デフォルトの名無しさん:04/01/15 08:33
c言語dlできるサイト教えてくれ
>>10
> 全てを同時にということです。

ベクトルプロセッサとかでないと難しいと思う。
13デフォルトの名無しさん:04/01/15 08:41
>>10
よくわからんが、関数に二次元配列を渡す方法を知りたいのか?
14ヽ(´ー`)ノ:04/01/15 09:00
>>11
>>2
好きなの選べ。環境言わないからオススメは言えない。
15デフォルトの名無しさん:04/01/15 09:27
質問なんですけど
C言語でローカル変数に大きい配列を宣言すると
どうしてコンパイルエラーが出てしまうんでしょうか?
16デフォルトの名無しさん:04/01/15 09:36
>>15
intを越えるようなことをしなければコンパイルエラーにはならないと思うけど・・・
実行時エラーか?それならおそらくスタックがあふれるから。
17デフォルトの名無しさん:04/01/15 09:47
でかい配列を使うときはプログラムが動かなくなるから
グローバル変数を使えといわれたんですが・・・
コンパイルエラーとはちょっと違うのかも
スタックがあふれるってどういうことでしょうか?
18デフォルトの名無しさん:04/01/15 09:56
>>17
大抵の環境でauto変数はスタックと呼ばれる領域におく。
そしてその大きさ以上にスタックを消費するとあふれる。

> グローバル変数を使えと
そういう理由でグローバル変数にするのは感心しないなぁ。
staticをつけるかmallocを使えば解決するかも。
前者は薦められないけど。
19デフォルトの名無しさん:04/01/15 10:01
なるほど
参考になりました
ありがとうございました
20デフォルトの名無しさん:04/01/15 16:40
>>10

質問がいまいちよくわからんけど、
mainと別にもう1つ関数を定義して、
その引数として配列を渡したいということ?

void MySort(int *array){ 関数の中身 }

main(){
int a[5][2];
値の入力
MySort(a);
}

って感じになるのでは。
2次元配列の渡し方か?

void unco(int s[][5]){



}

のように後ろの要素数だけは省略せずに書く。
22デフォルトの名無しさん:04/01/15 16:47
imcompatible pointer type
2310:04/01/15 16:49
すいません。書き方が悪かったです。結局調べて何とか動かすことはできました。
でも肝心の並び替えの部分がどうもうまくいかないんです。
以下にできたとこまで書きます。メインのとこは省きます。

/* 関数 並び替え */
int kansu_change(int ch[][2])
{
int work,i,j;
for(i=0;i<4;i++){
for(j=i+1;j<5;j++){
if((ch[i][0]<ch[j][0])||((ch[i][0]=ch[j][0])&&(ch[i][1]<ch[j][1]))){
work=ch[i][0];
ch[i][0]=ch[j][0];
ch[j][0]=work;
work=ch[i][1];
ch[i][1]=ch[j][1];
ch[j][1]=work;
}
}
}
printf("ソート後:");
for(i=4;i>=0;--i)
printf("%d/%d ",ch[i][0],ch[i][1]);
printf("\n");
return 0;
}

自分ではこれでいいと思うのですが並び替えがうまくいきませんでした。
助けてください。
24デフォルトの名無しさん:04/01/15 17:00
ifの中を==にとか
いまいちやりたいことがわからん
データすべてに対してってのがa[0][]とa[1][0]のソートをそれぞれ同時に
行うって意味ならこんな感じか?
int kansu_change(int ch[][2])
{
int work,i,j;
for(i=0;i<4;i++){
for(j=i+1;j<4;j++){ //ここは5じゃなく4
if(ch[i][0]<ch[j][0]){
work=ch[i][0];
ch[i][0]=ch[j][0];
ch[j][0]=work;
}
if(ch[i][1]<ch[j][1]){
work=ch[i][1];
ch[i][1]=ch[j][1];
ch[j][1]=work;
}
}
}
printf("ソート後:");
for(i=3;i>=0;--i) //ここは4じゃなく3
printf("%d/%d ",ch[i][0],ch[i][1]);
printf("\n");
return 0;
}
2610:04/01/15 17:11
>24
見落としてました。でも=でも動いたんですけどねえ。
27デフォルトの名無しさん:04/01/15 17:13
そりゃ=でも動く。文法は正しいのだから。
>>10さん、質問の意味なんですが、

考え方としては
負数は今考えないものとして
ch[4][2]={
{a,b},
{c,d},
{e,f},
{g,h}
}
とした時、4つの整数ab, cd, ef, gh を作って(a=23, b=4 ならばab=234)
この4つをセレクションソートで降順にソートしたのを昇順で出力したいって事ですか?


goto は使わないほうが良いと聞きましたが何故ですか?
>>29
gotoを使うとその人はいいだろうけれど、管理がしづらい
つまり、その後を次ぐ人が、ソースコードの理解をするう
えで、わけわからんことになりやすいため

それこそ、ソースコードの中で迷子になることにつながる

ポインタを使いましょう
ただし、ポインタならなんでもいいのかといったら、それを使いすぎると
やっぱりgoto文と同じで迷子になるきっかけになり

バグトレースがしにくくなるので辞めましょう
3228:04/01/15 23:59
>>10さん、もし..>>28の意味でいいならこうなります。
for(i=0;i<3;i++){
for(j=i+1;j<4;j++){
if(ch[i][0]<ch[j][0]){
work=ch[i][0];
ch[i][0]=ch[j][0];
ch[j][0]=work;
work=ch[i][1];
ch[i][1]=ch[j][1];
ch[j][1]=work;
}
else{
if(ch[i][0]==ch[j][0]){
if(ch[i][1]<ch[j][1]){
work=ch[i][0];
ch[i][0]=ch[j][0];
ch[j][0]=work;
work=ch[i][1];
ch[i][1]=ch[j][1];
ch[j][1]=work;
}
}
}
}
}
33つまった:04/01/16 00:19
#include <stdio.h>

void func_0(char);
void func_t(char);
void func_th(char);
void func_the(char);
int count = 0;
void (*next_func)(char) = func_0;
void func_0(char c) { next_func = (c=='t')? func_t : func_0;}
void func_t(char c) {
if(c=='h') next_func = func_th;
else func_0(c);
}
void func_th(char c) {
if(c=='e') next_func = func_the;
else func_0(c);
}
void func_the(char c) {
count++;
func_0(c);
}
int main(void) {
int ch;
while( (ch = getchar() ) != EOF )
(*next_func)(ch);
printf("count=%d\n",count);
return 0;
}
34つまった:04/01/16 00:22
33なんですがうまくうごいてくれません。
33は文を入力して単語の一部に"the"という綴りが現れた回数を数えるプログラム
「単語の区切り」は、スペース(' ')又は改行('\n')のみ考えればよいとする。
というものです
宿題スレに戻れ
36デフォルトの名無しさん:04/01/16 00:44
めちゃめちゃトリッキーなコードだな。
>>30
ポインタとgotoに何の関係が?
38デフォルトの名無しさん:04/01/16 02:02
>>37
コピペに反応するな
>36 に同意

せめて関数ポインタのてーぶうを使うべき
ってゆーかそこまでする必要もないか
while( (ch = getchar() ) != EOF )
switch(ch){
case 't': s=(s==0)?1:0; break;
case 'h': s=(s==1)?2:0; break;
case 'e': s=(s==2)?3:0; break;
defalt: if(s==3) ++count;
s=0;
}
if(s==3) ++count;

で十分
defalt ?
42デフォルトの名無しさん:04/01/16 05:52
>>32
そういう意味ではなく、data[0][0]に一番大きな値が入り、
data[0][1]に二番目に大きな値が入り、
data[3][1]に一番小さな値が入るようにしたいのです。
4342:04/01/16 05:54
こういう質問は別スレですね、、すいませんでした
「配列」を並べ替えるってのがそもそも意味わからん。
「配列の中身」を並べ替えるんだろ?
45デフォルトの名無しさん:04/01/16 14:05
純粋仮想関数はインターフェースのようにつかうのでしか?
>>45
C++ ですか?
カントの純粋理性批判でも読め。
48デフォルトの名無しさん:04/01/16 16:13
>>46
C++でし。
スレ違い。
50デフォルトの名無しさん:04/01/16 16:27
わかる人だけ答えてくれればいいでし。
51デフォルトの名無しさん:04/01/16 16:33
>>50
なんだその態度は!
わかるわからないのそういう問題ではない。
このスレはC言語についてわからないことを
聞き、また答えるためのスレだ。スレ違いな
話でスレを消費するのは迷惑だ。
>>52
放置汁
5448:04/01/16 17:16
>>50
別人
>>52
そういう態度もどうかと思うよ。
5652:04/01/16 18:49
>>55
なんなんですか?
あなたはスレ違いを犯し、さらに
惚けた態度をとった人間(別人だったらしいが)に注意する
ことがおかしいことだというのですか?
悪いものを悪いと言えないあなたの姿勢には
問題が多分にありますね。即刻謝罪をしてもらいたい
ですね。プログラマだからなんでも許されると思ったら
大間違いなのですよ?
なんだネタ野郎か
5852:04/01/16 19:28
>>57
まともに議論する気はないようなので、これで失礼させていただきます。
実に不毛な時間でした。無能な人間を相手にすると実に疲れます。
この場合は感情的になった方が負け。
というより、何でこの程度で激怒するの?俺には理解不能。
ネタだろ。
面白くないけど。
Windowsの標準エラーのファイルを変更するにはどうしたらいいですか?

Linuxはたしか >& でしたよね?
2> ファイル名
とかじゃなかったかと。
Cに関係あるか?
dup2(2, "/dev/hage");
>>62

ありがとうございます、その方法でなんとかなりました。
>>65のシステムはNT系と判明。
67デフォルトの名無しさん:04/01/16 21:07
9x 系は確かエラー出力のリダイレクトができないんだっけ?
9xっつーかcommand.comはできない。
パス補完どころか、ヒストリも使えないあんなシェルは逝ってよし。
ヒストリくらいdoskey使えよ
それ以前に果てしなく使いものにならないのだが、
そもそもスレ違いなので逝ってよし>>61-71
7252:04/01/16 22:12
>>60
なんですか、そのふざけた物言いは。
おもしろい、おもしろくないがすべてだと
思っているみたいですね。一体今まで
何を教わってきたのですか?
>>72
君、もう面白くないから書き込まなくていいよ。マジで。
74デフォルトの名無しさん:04/01/16 22:26
>>73
頼まれたっているかこんなスレ
氏ねバカ。
7561:04/01/16 22:38
いや、一応C言語のストリームを勉強していたんで・・
76デフォルトの名無しさん:04/01/16 22:46
すいません、質問させてください。
int型で要素数が5個の配列を複数個分メモリを確保したいのですが、
それがN個なら int data[N][5] とすれば良いのでしょうけど、
不定個なため動的に確保したい時はどうすれば良いのか教えてください。
配列へのポインタ int (*data)[5] をいじるのかなと見当つけてるのですが・・。
77デフォルトの名無しさん:04/01/16 22:48
>>76
malloc
int[5]へのポインタを用いるというアイディアで間違ってない。
が、多次元配列の動的確保は
全ての要素をメモリ上連続に確保するか
文字通りの配列へのポインタ配列を確保するかで書き方が違う。
詳しくはC FAQ 6にある
7976:04/01/16 23:30
ありがとうございます。
data=(int(*)[5])malloc(sizeof(*data)*N);
のようにすれば上手くメモリを確保できました(多分)。
C だと void* からのキャストは不要なんじゃなかったっけ?
81デフォルトの名無しさん:04/01/16 23:49
>>80
プロトタイプ宣言さえあればOK
82デフォルトの名無しさん:04/01/17 00:14
ある文字列の初めから、
ある文字列の任意の位置までを取得したい場合はどうしたらいいですか?
部分文字列の切り出しのこと?
一番簡単で強力なのは sprintf
84デフォルトの名無しさん:04/01/17 00:32
>>82
strncpyして末尾に'\0'
もしくは
あらかじめ文字列長を0に切りつめたバッファにstrncat
strstr()を聞いてんじゃないのか?
8682:04/01/17 00:50
出来ました
ありがとうございました
それ比較じゃ。
>>85
strstrはsubstrじゃないぞ
>>88
「任意の位置までを取得」か。
位置を取得と勘違いした。
ま、もし書き換えてもいいんなら
末尾に当たる位置に0入れりゃいいだけなんだけどな
91ヘタレ:04/01/17 03:31
vc++スレで聞いたらcスレで聞けと言われてきました。
リスト処理でvalueがkeyと等しい場合にTRUE 1、
等しいものが無かったらFALSE 0を返す関数existを作ったんですが
return FALSE;のところでAccess Violationが出てしまいます。
これは何が悪いんでしょうか。VC++6.0 SP5を使っています。
宜しくお願いします。

struct list {
int value;
struct list *next;
} l;
bool exist(struct list *l, int key) {
if (l->next == NULL) {
return FALSE;
} else if (l->value == key) {
return TRUE;
} else {
return ((exist(l->next, key)));
}
}
if (l == NULL)
生成されるコードは同じだけど
処理のブロック分けをきちんとしてれば今回の問題は避けられたろうに。
それにしてもこの処理内容で真偽値だけ返すのはもったいないね。

struct list* find(struct list *l, int key) {
if ( l == NULL)
return NULL;

if (l->value == key)
return l;
else
return exist(l->next, key);
}

/* inline 化したい */
bool exits(struct list* l, int key) {
return find(l,key) != NULL;
}
9491 ヘタレ:04/01/17 06:16
>>92>>93
レス有難う御座います。

Access Violationが出ていたのは
if (l->next == NULL)
if (l->value == key)
のところみたいです。すいません。
また、93さんの書いてくれたコードで
return exist(l->next, key) を
return (list*)exist(l->next, key) にキャストして
やってみたのですが、keyの値が無い場合に
if (l->value == key) のところで
やっぱり 0xC0000005: Access Violation が出てしまいます。
呼び出し方が悪いんでしょうか。
ただのif文の判定に使っているのですが。

struct list* find(struct list *l, int key) {
if ( l == NULL)
return NULL;

if (l->value == key)
return l;
else
return find(l->next, key);
}

修正し忘れだな。
つーかこんな構造にする必要がないのなら
>>92の通り最初だけ if( l == NULL ) と直せばいいんだ。
>>94
とにかく、l がどんな値かわからんのに、いきなり l->next なんてコードを書くな。
>>92-93, >>95 が言うようにきちんと NULL でないことを確認する癖つけないと、今後またはまるよ。

あと、これって学校の宿題かなんかか ?
学習とかポリシーとか趣味とかでないなら、わざわざ再帰を使う必要はないと思う。

struct list* find(struct list *l, int key) {
 while(l != NULL && l->value == key){
; l = l->next);
 return l:
}
>>96
間違えて途中で書き込んじゃった。

struct list* find(struct list *l, int key) {
 while(l != NULL && l->value != key){
  l = l->next;
 }
 return l:
}
馬鹿なやつほど再帰とか使って分かりにくくするんだよな。(藁
>>98
数学できないだろ。再帰の方が簡単だよ。遅いけど。
>>99
この程度ならどっちもどっちだろ。> 簡単さも速度も。
>>100
そうだな。だが>>98は一般論だろう。
>>101
そうか、再帰使えば簡単な奴を必死になって自分でスタックもどき作ってがんばるお馬鹿もいるぞ。
無駄で C に関係ない議論だ。やめれ。
char * s ;
s = "abcdefg" ;

"abcdefg"が開放されるのっていつですか?
普通の変数と同じ、ブロック内ですか?
105104:04/01/17 12:30
× 普通の変数と同じ、ブロック内ですか?
○ ブロック外に出たときですか?
文字列リテラルは、プログラムの終了時。
C99に準拠しているコンパイラって、gcc以外にありますでしょうか?
具体的には可変長マクロが使えるのを探しています。
108107:04/01/17 14:08
しまった。 OS書くのを忘れていました。
Win環境で使えるのを探しているんですが、検索してみたんですが
そこまで書いているページが見つかりませんでした。
>>106

それは main関数以外の関数で文字列リテラルを用意してもプログラム終了時まで保持されるということですか?

int main()
{
char *s;
s=f();
printf("%s\n",s);
return 0;
}

char *f(void)
{
char *s;
s="abcdefg";
return s;
}

こういう処理もOKってことですか?
良質なコードを以下に掲載しておく。

#include<stdio.h>
int main(void){
printf("Hello world\n");
}
>>110
そのような台詞は GNU Hello でも読んでから言いたまえ。
>>110
質をうんぬんする以前の問題だ。
113デフォルトの名無しさん:04/01/17 15:50
C言語初心者です。
キーボードから半角英数字からなる文字列を入力し、
非アルファベット文字を除いた文字列を出力するプログラムが分かりません。
どなたか分かる方がいたら教えて下さい。
>>107
MinGW の gcc でええんでないの?
>>113
#include <stdio.h>
#include <string.h>

int main() {
for (;;) {
int c = getchar();
if (isalpha(c)) printf("%c",c);
if (c == EOF) return 0;
}
}
  _, ._
( ゚ Д゚) ?
>>117
#include <ctype.h>
>>117
一応なくても大丈夫。
もちろん、あった方がいいけど。
>>118
string.hをインクルードするくらいなら、、、というか、間違えたのかな?
120デフォルトの名無しさん:04/01/17 20:44
以下のプログラムはどこかおかしいのでしょうか?
友達にだめだめだっていわれた・・・・

char *p = "test";
.
.
if(p != NULL & strcmp(p , "test") == 0) {
}

&&
&&&
123120:04/01/17 21:01
>>121 , 122
ちゃんと動いていますがどういうことでしょうか?
(ちゃんと理由かけよ、子供か、こいつら)
あれだけ端的に書かれてきちんと振り返らないお前が子ども。
とりあえず動けば正しいと思ってたらいつにたってもバグは取れんよ。
論理積は && だ。 & はビット演算。
125120:04/01/17 21:07
>>124
でもきちんと動いていますよ。どういうことなんですか?
(どこが端的だ、小学生並だな、ほんとに)
>>121見ても分からない奴に説明するような無駄なことに時間を浪費する程暇じゃないってことだろう。
どうもただの荒らしみたいだな。
本気かもしれんからもう一度言っておく。
「とりあえず動くコード」が「正しいコード」ではない。
120はただのつまんない釣りだって
これからは放置で。
&&&&
130120:04/01/17 21:13
>121-129
どこが悪いかわからないならレスしないでください!
(なんでこんなやつらに丁寧語使わなきゃいけないんだ。)
131120 ◆.D7dxTtRKs :04/01/17 21:14
ニセモノが居るようなのでトリップつけました。
132デフォルトの名無しさん:04/01/17 21:15
あー、あの本の販促か(w
133120:04/01/17 21:18
これからここは俺がしめるから。
閉店ですか?
まだ酔い足りない
次いくぞ、次
136120:04/01/17 21:21
俺は本当に120なのか
もうわからなくなってきた。
誰か教えてくれよ。
137120 ◆.D7dxTtRKs :04/01/17 21:23
解決しました。
&をもう一つ使えという事だったんですね!

char *p = "test";

if(p != NULL & strcmp(&p[0] , "test") == 0) {
}

(ほんとに回りくどいやつらだな。)
もうネタはいいよ。
次の質問カモーン。
>>900
そんなんで悩むやつが超スレにいるわけないだろ。
140139:04/01/17 21:28
誤爆。
>>109はやっても大丈夫なんですか?
>>120
もう少し面白いネタをよろしく。
143120:04/01/17 21:36
>>132
やっと気づいた人がでてきましたか。
>>141
やっても大丈夫だけど、
const char* で返す方が安全。
>141
"文字列リテラルがプログラム終了時まで保持されるということ"と
一時変数が保持される事とは
ちょいと違うぞ
>>145
>>109のプログラムのどこにその問題がある?
147109:04/01/17 21:50
どうも、ありがとうございます

また質問するかもしれませんが、そのときもよろしくお願いします(^o^)/
>>145
int foo() { int n = 32; return n; }

>>109 は文字列でこれと同じ事をしてるわけだが。
149145:04/01/17 21:57
そうですね。間違ってまいた。スマソ
>>148
少し違うだろ?
>>150
int foo() { int n; n = 32; return n; }

はい。これでいい?
int * f ( void ) { int n ; n = 32 ; return & n ; }
華麗にスルー
>>151-152
┐(´ー`)┌
>>154
int* f() { int* n; static int v = 32; n = &v; return n; }

と言いたいのか?
それはちょっと趣旨から外れてるぞ?
つーか質問者のプログラムに問題ないことははっきりしてるんだから
いつまでも揉めてるなよ
揉めてるんじゃなくて遊んでるんでしょ。
158もめ:04/01/18 04:29
int* f() { int* n=malloc(sizeof(int)); *n=32; return n; }
に近いな
159デフォルトの名無しさん:04/01/18 05:28
何言いたいのかわからん。
>>109は本当に大丈夫なの?
微妙に処理系依存だったりしない?
ポインタはアドレスである必要は無いんだし。
文字列リテラルはどこで宣言しようが永遠に存在する
っていう仕様は見たことが無いし。
組み込み系とかのことを考えると微妙な雰囲気が漂ってませんか?

K&Rを調べてみたけど見つからなかった。
詳しい人の降臨を望みます。
164デフォルトの名無しさん:04/01/18 20:08
>>162
永遠って何のことだ?
ホスト環境も組み込みの延長上でしかないぞ
調べるべき資料も間違ってるし・・・ (規格票じゃない)

そんなわけわからん電波発信しまくってると詳しい人いても逃げちゃうぞ
165デフォルトの名無しさん:04/01/18 20:33
質問です。

2chのdatファイルに関する事なのですが、
例えば

デフォルトの名無しさん<>sage<>02/05/25 09:29 ID:gInBgWb.<> おいおい <br> 変態か <>

こういう文字列から、「名前」と「ID」と「本文」を

struct data{
char name[100];
char id[15];
char text[10000];
}res[1];

こういう構造体にそれぞれつっこみたいときは、具体的にどのようにすればいいでしょうか。
IDだけとかを取得するのが難しいのです。
よろしくお願いします。(すれ違いだったらすいません)
2ch dat のことようわからんけど、データ毎の区切りがレスとグレータになってるみたいだけど・・?
txtendp=strstr(txttopp,"<>");
sprintf(tmptxt,"%.*s",txtendp-txttopp,txttopp);
名前欄とかに<>が入っていたらどうするの?
名前欄とかに < とかを書くとdatファイルの中では < なんかに置き換えられてるみたい。
失敗
&lt;
これの半角
まあ、HTMLっぽいしね
>>165
#include <string.h>
char *copy_to_delim(char *dst, size_t size, const char *src, const char *delim) {
  char *p = strstr(dst, delim);
  if (!p)
    return NULL;
  *p = '\0';
  strncpy(dst, src, size - 1);
  dst[size - 1] = '\0';
  return p + strlen(delim);
}
char *split2ch(struct data *d, char *src) {
  char *s = src;

  /* 名前 */
  if (!(s = copy_to_delim(d->name, sizeof(d->name), s, "<>")))
    return NULL;
  /* ID */
  if (!(s = strstr(s, "<>")) && !(s = strstr(s, "ID:")))
    return NULL;
  /* 本文 */
  s = copy_to_delim(d->id, sizeof(d->id), s + 3, "<>");
  if (!s)
    return NULL;
  return copy_to_delim(d->text, sizeof(d->text), s, "<>");
}
こんなの。split2chを呼ぶ。戻ってきたのがNULLだったらなんか変だった。
そうじゃなかったら、次のレスを指している(はず)。
元の文字列いじくるから気をつけてね。
>>163
すんません・・・FAQだったとはうかつ・・・

>>164
>ホスト環境も組み込みの延長上でしかないぞ
ROMから直接プログラムをフェッチして動いていて、
メモリマップ上にはROMの一部しか見えてなくて、
何らかの方法でメモリマップ上に見えるROMの領域を切り替える
っていう組み込み系のプログラムを見たことがあるので・・・
(あああ・・・うまく説明できない。MS-DOSのころもそうだったとか?)
>>173
> 何らかの方法でメモリマップ上に見えるROMの領域を切り替える

組込みとかでそういうことやることはある (昔は PC でもバンク切替とかやってた) が、そういうのは C 言語の範疇外で、プログラム側で処理する。
>>173
バンク切替えか。
見えなくなるだけで実体が無くなるわけじゃないだろう。
>>174 >>175
お返事どうもです。バンク切替というのですね。

>見えなくなるだけで実体が無くなるわけじゃない
まさしくココを勘違いしていました。
バンク切替をして(こういう使い方であってるかな?)一時的に見えなくなっても、
もとにもどせばまた見えるわけですからね。
すれ違いにもかかわらず、丁寧に教えてくださってありがとうございます。
177177:04/01/18 21:49
#include<stdio.h>
#include<string.h>
int main(void){
char s[1024],*pat="the",*p=s;
int count=0;
printf("文字列入力\n");
fgets(s,1024,stdin);
while((p=strstr(p,pat))!=NULL){
count++;
p+=strlen(pat);
}
printf("count:%d",count);
return 0;
}
というプログラムがあるんですがwhile{}のところでなにをしているのかよく
わかりません。
どなたか教えていただけないでしょうか
永遠なのか?本当か?
時の流れは続くのか?
>>177
char *strstr(const char *s1,const char *s2)
文字列s1の中に最初に現れる文字列*s2を検索し、
見つけた文字列へのポインタを返す。見つからなかったらNULLを返す。
s2が長さ0の文字列なら、s1の値を返す。

while((p=strstr(p,pat))!=NULL){ /* 文字列p中からpatを探してそのポインタをpに返し、それがNULLでなければ */
count++; /* countを1増やし、*/
p+=strlen(pat); /* patの文字数だけpを進め、次に検索する際、同じ部分を検索しないようにする*/
}
かな。
>>177
pがさすところからpatに入ってる文字列を検索。
あれば、その見つけた位置をstrstr()は返すから
とりえずカウントアップして、その探し出すパターンの長さ
分進めて(pはtheのtの位置をさしてるからeの次まで進めてる)   
そこからまた検索。見つからなかったら
strstr()はNULLを返すからwhile文の条件式はそうなっている。

それ改行読み込めないから、確か問題の回答にはそぐわなかったけどね。
かぶった。
182165:04/01/18 22:06
>>172
いろいろ解決しました。
ありがとうございました。
183177:04/01/18 22:07
>>179
>>180わかりましたーありがとうございます。

>>180改行を読みこむにはどうしたらいいんでしょうか?
ネットでいろいろしらべてたんですが、BM法というやつらしいですね。
>>183
ん?BM法は単にstrstrの部分に相当することをやってるだけ
だから関係ないんじゃないかな?
fgetsのかわりにgetcharとか使えば改行も読み込める。
でも確かこの問題はstring.hを使っちゃだめな問題だった気がするけどね。
問題の質問者じゃなければ関係ないが。

#include<stdio.h>
#include<string.h>
int main(void){
char s[1024],*pat="the",*p=s;
int count=0,ch;
printf("文字列入力\n");
while((ch=getchar())!=EOF)
*p++=ch;

*p='\0';
p=s;
while((p=strstr(p,pat))!=NULL){
count++;
p+=strlen(pat);
}
printf("count:%d",count);
return 0;
}
185177:04/01/18 22:40
>>184
えーとー、、、その、ずばり自分です(滝汗
186177:04/01/18 22:43
あ、つかっちゃいけないのはstrcmpでした。
どうもありがとうございました。
でもstrcmp等を使っちゃダメってことは
string.h自体を使うなってことだと思うんだがな。
宿題で出すんであればぼるじょあスレで出てた
他のやつ使ったほうがいいカモ。
188177:04/01/18 23:08
あの他の人に出してもらったやつ上手いことうごいてくれないんですよね
読んでもワケわからなかったですしお手上げです(^^;

あと184をコンパイルするとundefined reference to 'getcher'ってでてくるんですが
これはどうやったらエラーでないでコンパイルできるんでしょうか?
なんか質問房みたいですみません

getchar
>>188
ヽ(゚∀゚)ノ ガーン!
>>188
漏れの知り合いにもいるが例え英語でもエラーはちゃんと読もうな・・
すいません 昔の友人が明日進級がかかった大学の試験があるのですが、
C言語でforを二度使って例文を作り解説をしなさいという問題が出題される
がまったくわからないらしくて聞いてきました。
私もC言語がわからないのでどなたか教えていただけないでしょうかm(_ _)m
ずいぶんと友人想いだな
(・∀・)♪
おとなしく留年した方が・・・
前日まで対策してないってのはちょっとなあ。
すいませんm(_ _)m
私の責任ではないのですが、なにぶんにも古くからの友人のため・・・
とりあえず、C言語入門のHP見て何とか考えてはいるのですが、
なかなかforを二度使った使用例みたいなやつがないので・・・
俺はもう眠いので、誰か暇な人、適当なコードをでっち上げてやってください↓
いやならいいです。
是非、友達には留年してもらおう。
本人はそんなに必死じゃないみたいだし。
#include <stdio.h>

main()
{
int i,j;

for(j = 1; j<= 9; j++)
for(i = 1; i <=9; i++)
printf("%dかける%dは%d\n",j ,i ,j*i);
}


世にも不思議な九九を自動表示してくれるプログラムだ
しょうがく二年生が飛びついてくるぞ
>>199
先越されたw
char *str="た\0け\0や";
int i;
for(i=0; i<=2; ++i) printf("%s ",str+i*3);
printf("ぶ ");
for(i=2; i>=0; --i) printf("%s ",str+i*3);
そりゃ回文だ
取って置きのソースコードを伝授してやろう

void main(void)
{
#define _
#define m
#define __ ;

for (;_;) /* ゴウカクサセテ */

for m(__ __)m /* コノトオリ */
}
>>203
無限ループのネストってはじめてみた
>>201
>>204
嘘でしょ・・・?
206203:04/01/19 00:56
>>205
いや、ちゃんとコンパイルとおるよ
>>204も驚いてるジャン
これって平凡に見えて誰も思いつかない実はすごいコードなんだよ
行列の足し算でもいいな。
>>203 は通らない希ガス。
2番目の for の実行文がない。
なんだこの自意識過剰の203が居るスレは
バブルソートってのは?
件の奴には荷が重いか。
直接選択ソートの方が
int tmp,i,j,x[]={1,3,5,2,4,6};
for(i=0; i<sizeof(x)/sizeof(int)-1; ++i)
for(j=i+1; j<sizeof(x)/sizeof(int); ++j)
if(x[i]>x[j]){ tmp=x[i]; x[i]=x[j]; x[j]=tmp; }
逆順で表示したいけど、いい方法はないですか

#include <stdio.h>
#define BYTESIZE 8

int main(void)
{
 unsigned user_number, i;
 unsigned typesize = sizeof(unsigned);

 printf("正数入力...");
 scanf("%u", &user_number);

 for(i=0; i < typesize*BYTESIZE; i++) {
   printf("%u", (user_number>>i) & 1);
   if(!((i+1)%BYTESIZE)) printf(" ");
   }

 return 0;
}
>>208
ホントダ
2番目のforは
;がないな
>>212
そんなアナタにスタック!
中だし先入れ?
後入れ中出しだよ。
それを言うなら、入れだし入れだし(どp)
はやっ!
>>212
とりあえず、ループ逆にすれば?
スタックの概念がよくワカラネ けど、

unsigned stack[TEKITOU];

stack[i]=((user_number>>i)&1);
i--;

for(;i;i--) {
 printf("%u",stack[i]);
 }

こういう感じですか
>>212
そんなあなたに再帰関数
221212:04/01/19 01:36
>218
どうすれば逆に...

>220
始めは再帰を使おうと思ったんですが、サッパリで

再帰とビットのことを考えるとトリップします。
for (i = 1 << (BYTESIZE * typeseze - 1); i > 0; i >>= 1)
よくわからんが。
int main(void)
{
 unsigned user_number;
int i;
 unsigned typesize = sizeof(unsigned);

 printf("正数入力...");
 scanf("%u", &user_number);

 for(i= typesize*BYTESIZE - 1; i >= 0; i++) {
   printf("%u", (user_number>>i) & 1);
   if(!(i % BYTESIZE)) printf(" ");
   }

 return 0;
}
こんなんか。
#include <stdio.h>

void binary(unsigned char n);

int main() {
 unsigned int n;
 printf("正数入力 > ");
 scanf("%u", &n);
 binary(n);
}

static void binary_(unsigned char n) {
 if(n != 0) {
  binary_(n >> 1);
  printf("%u ", n & 1);
}
}

void binary(unsigned char n) {
 if(n == 0) {
  printf("0");
 } else {
  binary_(n >> 1);
  printf("%u", n & 1);
 }
}
>>224
for(i= typesize*BYTESIZE - 1; i >= 0; i--) {
だった。
というか、固定長か。
固定長ならバッファに貯めて逆順に表示すれば
(もしくは逆順に貯めて表示すれば)いいだけだったな。
228212:04/01/19 01:50
みなさん書き込みありがとうゴザマス

とりあえずパッと見で理解できるほどLVが高くないので、
いろいろいじって理解させて頂升。
>>228
まあ、いろいろやって見れ。
230デフォルトの名無しさん:04/01/19 17:58
動的配列のサイズを取得するにはどうしたらよいでしょうか?
231ヽ(´ー`)ノ:04/01/19 18:02
>>230
malloc で確保した領域ならサイズの取得は無理。
232113:04/01/19 18:17
>>115
インクルードするのは<stdio.h>だけで書けませんか?
233115:04/01/19 19:09
>>232
ポータビリティはよくわからないけど。

#include <stdio.h>

int main () {
    int c;
    while ((c = getchar()) != EOF) { // 少しCを思い出した
        if ((('A' <= c) && (c <= 'Z')) || (('a' <= c) && (c <= 'z')))
            putchar(c);
    }
}
return について、質問なんですが、

int func(void){
return 1;
return 2;
return 3;
};
ってすると、funcの値は、1でしょうか?3でしょうか?
もし、この結果が1で返るなら、これを使って関数の深い部分から一気に抜け出したいのですが・・・。

初心者な質問ですみませんm(_ _)m
>>234
やってみればいいのに。1です。
>>235
即答でありがとうございます。
コンパイル環境がなかったもので、、済みません
つまり、return;後の処理は全部とばしてしまうんですね。
C言語の問題です。
フィナボッチ数列を100個表示させるプログラムを作れ、
というものです。一次配列を使わなくてはならないのですが
混乱してしまいどうしようもありません。お願いします。
一応・・・↓

include <stdio.h>
#include <stdlib.h>
#define N 100
main()
{

int fib[N+1], i, n=10;

fib[1] =1;
fib[2] =1;

for (i = 3; i < n ; i=i+1) {
fib[i] = fib[i - 1] + fib[i - 2];
printf("%d\n",fib[i]);
scanf("%d",&fib[i]);
   }
}

よろしくお願いします。
あるルーチンのなかで、メモリーを大量に確保している部分があります。
そのメモリーを解放する部分が、そのルーチンの一番最後にコーディングしたんですが、
returnで、抜けちゃおうと思っていたんですが、するとメモリー開放をせずに抜け出しちゃうので、

rutin(){

malloc(メモリー確保部)

if( ){ a=1; goto END; }
if( ){ a=2; goto END; }
if( ){ a=3; goto END; }

END:
free(メモリー開放部)
return a;
}

のように、回避しています。
gotoを使わずに、同様の動作をする方法をご教授下さいm(_ _)m
Cでは無理
241239:04/01/19 21:22
#define N 100
#define M 100
main()
{
char *pat,line[N],deline[N+1],b[N],*x=line;
int z=0;
while (1){
printf("\n");
printf("文字を入力してください\n");
printf("終了したいときは end と入力してください\n");
fgets(line,N,stdin);
if((line[0]=101)&&(line[1]=110)&&(line[2]=100))break;
printf("%c",line);
printf("\n");
/*1つ前にずらすプログラム*/
printf("文字を一字左にずらします\n");
for(z=0;z<sizeof(line);z++)
{deline[z]=line[z+1];}
printf("%s\n",deline);
/*1つ後ろにずらすプログラム*/
printf("文字を後ろにずらします\n");
for(z=0;z<sizeof(line);z++){
deline[z+1]=line[z];}
deline[0]=32; /*ascii space*/
printf("%s\n",deline);

/*逆順にするプログラム*/
printf("文字を逆順にしますよ");
for(z=sizeof(line);z>=0;z--){
putchar(line[z]); }
printf("\n");
242上間違い241:04/01/19 21:23
こんなんつくったんですが。
endいれる前に終わってしまうんですがどうしたらいいでしょうか?
>>242
そらー、下まで行って終わるよな。
ところで"end"入力を確認する気が無いように思えるのは気のせい?
244上間違い241:04/01/19 21:31
12行目でやろうとしてるんですが
>>241-244
    if((line[0]=101)&&(line[1]=110)&&(line[2]=100))break;
これでbreakしてる。
line[0] == 'e' && ...
になおせばよい。
# 文字コードを数字で書くな。
>>239
やってできないことはない。
>>240
知恵も知識も足りないのに断定するな。
rutin() /* るちん? */
{
int a;
void *pMem = malloc(SOMESIZE);
switch (1) {
case 1:
if (CONDITION1) {
a = 1;
break;
}
case 2:
if (CONDITION2) {
a = 2;
break;
}
case 3:
if (CONDITION3) {
a = 3;
break;
}
default:
break;
}
free(pMem);
return a;
}
>>244
ごめん、まじめに見たところ12行目が悪いようです。
if((line[0]=101)&&(line[1]=110)&&(line[2]=100))break;
line[0]==101のように比較は==とすべき。
ハゲシクキモイ
>>246
なんだそりゃ? case文に何の意味が?

普通は

do {
    ...
    if (condition0) { ...; break;}
    if (condition1) { ...; break;}
    ...
} while(0);

だろ:-)
>>246
switch (1) { てあんた・・・
>>239
そりゃ頭をつかえばいろいろあるけど、
if文をブロックにしてしまって、それぞれに
free()とreturnを書いてしまえば済む話。

つーか、まったく同じ場面に今日出くわしましたが
迷わずそうしました。

#コードが長くなるのはイヤだけど、デバッグが複雑になるのはもっとイヤ。

252239:04/01/19 22:03
>>249
ありがとうございます。えっと、>>239のは、めちゃくちゃ簡略化してかかれていて、
本当は、
rutin(){

malloc(メモリー確保部)
↓コレ全体も深い階層にあって、そこから一気にGotoで抜け出しています。
-----------------------------------------------------
if( ){ a=1; goto END; }
if( ){ a=2; goto END; }
if( ){ a=3; goto END; }
-----------------------------------------------------
この部分も超〜長い
----------------------------------------------------
END:
free(メモリー開放部)
return a;
}
だから、break; do{ }while(0) という、使い方も避けたいのですが、他に方法ありませんか?
break一回だと抜け出せない深さにあります。
>>251

mallocで配列を確保しているのですが、その数が膨大で、且つ、if分それぞれで、同じものを使うので、
とちゅうで、freeを使うわけにもいきません。プログラムの最後で一括開放したいです。
時には、性能が保守性より大事なこともある。
開放部分を関数に分ければ
>>239
悪いことは言わん、関数を分けろ。

>>246
case文ってなんだ?
>>239
/* こんなんどう? */
rutin()
{
/* メモリ確保 */
a = originalRutin();
/* メモリ開放部 */
return a;
}
rutin
血液さらさら
>>256-257
もちろん、関数には分けてますが、それこそ100個ぐらいの関数分けをして、
rutin(){}
も、その関数の一つで・・・・

if(){ このなかにも、関数分けしたものが、山ほどあって・・・}

ifの部分は、その関数群をつかって、最大限減らした処理なんです。
あまり、関数分けすると引数が山のようにでてきて、それだけで欝になります。
関数名も思いつかないし・・・。
Cというよりは設計法の話になりつつあるような。
これからこのスレではrutinを標準にするのか。何語だ?
263249:04/01/19 22:26
>>260
p = malloc..
rutin(p)
free
ではいかんのか?
264239:04/01/19 22:27
すみません><
綴りわかんなかったので、理解してくれるだろうと思い、適当にrutinにしてしまいました・・。
routine
て、書きたかった・・・。るーちん るーちん るーちん
「この部分も超〜長い」の部分が最初に来るように、分岐条件を並べ替えられないの?

まぁ、GOTOでもいいじゃん。

こんだけ複雑なら、
if( ){ a=1; free(p); return; }
if( ){ a=2; free(p); return; }
if( ){ a=3; free(p); return; }

のほうが却ってみやすいぐらいだと思うけど。
俺も基本的には「呼び出し前に確保してポインタを渡し、呼び出し後に解放」
とすべきだと思うけど
場合によっては
「ポインタのポインタを渡して呼ばれた側で確保して代入、
呼び出し側に戻ってから(NULLチェックして)解放」
ってのもアリかなと思う。
267239:04/01/19 22:43
>>265
もう、Gotoつかうしかないっぽい・・・
ただ、Goto つかっちゃうと、例えば、

if(){goto;}〜
if(){ for(int i =1; i<=n; i++); }
みたいに、とちゅうで、int i みたいな宣言をいれると初期化エラーになっちゃうので、
初めに、これまたどうでも良い変数も宣言しておいて、

int i,j,k,〜;

if(){goto;}〜
for(i=1;i<=n;i++){}

にしなければならなくて、239の質問をしました。む〜goto使うなってよく言われるけどもうだめぽっ 
>>239

rutin2(メモリ){

if( ){ return 1; }
if( ){ return 2; }
if( ){ return 3; }

}

rutin(){

malloc(メモリー確保部);
a=rutin2(確保したメモリ);
free(メモリー開放部);
return a;

}

rutin2 の部分が単純なら
goto 使ったんでもいいとは思うけど。
269239:04/01/19 22:48
if( ){ a=1; free(p); return; }
if( ){ a=2; free(p); return; }
if( ){ a=3; free(p); return; }

これも、事情によりできません。というか、pにたいして、さまざまな値が代入されるわけですが、
その値を求める処理がこれまた超重で、一度与えられたpの値をfreeで開放してしまうと、2度手間3度手間・・・。
これら一連の処理を高速で行うためにも、freeは最後でやらんとだめなんです。
処理速度まで求めるのかーーーーーー
遅いと、困るプログラム作ってますw
>>265
if( ){ free(p); return 1; }
if( ){ free(p); return 2; }
if( ){ free(p); return 3; }
やね。

>>269
>>239>>265 とで何が違うのか分からんのやけども。
return 前に free してるんだから、別に何も困ることないでしょ?
諦めて、gotoでいきます。
これにて、終了。
なんか、goto使うと下手糞ってレッテルが貼られているような気がして、これまで頑なにgoto避けてきたんだけど、
一度使うと、逆切れしてgoto使いまくりたくなりますね。
深い、階層をもったプログラムをgotoなしで、どうやってみなさんは抜け出ているんでしょう・・・。
プロは goto を的確に使う。
100% goto を避けるのは素人。
>>272
あーなるほど、よく考えませんでした。
そういうことか〜。
でも、それって、free(p)が1まとまりの関数になっているわけですよね?

もしくは、free(p1)〜free(pN)ってなるとまたプログラムが長くなるし、
プログラムはもっと複雑なので、
if(){

free(p)が山ほどありゅ。
}
> 100% goto を避けるのは素人。

というかただのアホ。
gotoはインターフェイスを変更出来る権限があれば
使わなくてすむんだけどな
if(){ (´ー`)y−~~~ Goto
if(){(´ー`)y−~~~ Goto
if(){(´ー`)y−~~~ Goto
if(){(´ー`)y−~~~ Goto
}
}
}
}(´ー`)y−~~~ Goto
>>275
なるほど。そういうことか。
ところで >>268 はどうなの?
>>279

>>268
は、う〜む。rutin2 に、引数pをいぱ〜い渡さなきゃいけないからイヤダなぁ。
皆さんは、関数に渡す引数は、何個までならゆるせる?
俺は、どんなに我慢しても、20個が限度だな。10個以上だと腹が痛くなる。
構造体を使ってごまかしてみる。というアフォな考えを持ってるボクはアフォですか?
double_freeを恐れる気持ちはわからんでもない。
>>280
まあ、そんな事態になるまえに普通は構造体を定義するもんだけどね。
構造体は場合によって使えん環境もあるから。

free()は自作の関数じゃなくて、malloc()のメモリを開放するのをその都度かけって意味だよ。
goto - free() - returnよりは
その場で
free() - return しちゃったほうが早いんじゃないの?ってコトなんだけど。
どうせ開放するポインタは全部同じなんだし、解放後にすぐ関数から離脱するので
二重に開放する危険も少ないだろうと。
構造体にまとめるのは普通の手段だと思うが。
285239:04/01/19 23:35
>>281
現実的だと思うけど、ど素人の漏れは構造体に慣れてないので使いこなせない。
中学のころ、英語をかなり上手に筆記体で書くやつがいたけど、
そいつに、読めるの?って聞いたら読めないといったあふぉがいた。
そんな状態におちいりそう。
>>285
構造体はCをやる上で十分常識の範囲内だから、そんなに恐れなくても大丈夫だよ。
なんだ、こんな便利なのどうしていままで使わなかったのか、と思うよ。

言語オタクもどうかと思うけど、みんなが当然知ってることを知らずに仕事するのは
タダの徒労。
#defineで余計なマクロくんでデバッグに苦しむのはタダのアホ。
たとえ、returnの直前でも、free()がいくつも有るのは気持ち悪い。
そのうちreturnの直前でなくても、free()をばらまきそうだから。
構造体を使わないということは
C の機能 50% も使ってないのと同等だ。
そうか〜
構造体もっかい勉強しよかな。数学的なプログラムとかしか組まなかったから、
いまいち使い道が分からなかったので避けてきたけど、
構造体、共用体果ては、クラスまで使いこなせるようにがむヴぁる。

>>287
でも、わざわざ変数aを設定してまで戻り値をreturnのあるブロックに持っていく
このプログラムのような状況なら、おれはさすがにfree()の数にはこだわらん。
タブがそろってるし、見間違いもないかぁと割り切って先に進む。

むしろ、共通のブロックだということを忘れて、ENDブロックに何か書きそうで怖い。
見た限り>>239は設計がクソなだけ。
再設計するのが一番いい。
>>291>>239 を再設計します。
ところが結局、言うことはいうけど使えないヤロウだった・・・
というパターンだなこりゃ。

「再設計するのが一番いい」←プンプン臭う
294デフォルトの名無しさん:04/01/20 10:11
構造体について疑問が有るので、教えてください。
現在、技術評論社の柏原正三先生のC言語関連の本で独学中なのですが、
疑問に思う事が有ったので。

構造体には、内部で更にネストが可能であり、ネストメンバーのデータにアクセス
するには、「構造体変数.ネスト.メンバデータ」としなければならないそうなのですが。
ところが初期化の際には、何故か、ネストされてるメンバデータに、直接値を代入しているのです。
アクセスには、2段階必要なのに、初期化の際には.演算子などでの段階的な初期化代入が
不要なのは何故なのでしょうか???

「そういうもんだ!」と納得しなければならない話なのでしょうか???
struct foo_ {
int foo1;
struct bar_ {
int bar1;
int bar2;
} bar;
int foo2;
};

とあったとすると、まともなプログラムなら

struct foo_ f1 = {10, {20, 30}, 40};

こう書いてあるはずだが、まともじゃないのは

struct foo_ f2 = {1, 2, 3, 4};

こう書いてあったりして混乱する。
296ヽ(´ー`)ノ:04/01/20 10:34
C99 派な俺。

struct foo_ f1 = {
.foo1 = 10,
.bar = {
.bar1 = 20,
.bar2 = 30,
},
.foo2 = 40,
};
>>296
> C99 派な俺。
なら定義順に書くより名前順とか意味に合わせて並べないか?

struct foo_ f1 = {
    .foo1 = 10,
    .foo2 = 40,
    .bar = {
        .bar1 = 20,
        .bar2 = 30,
    },
};
298ヽ(´ー`)ノ:04/01/20 11:34
>>297
それを言うなら、そもそも定義する時に名前順にするよ。
>>294
そういうもんです。

しかし、
アクセスの時には、中身の構造体が外のメンバと同じ名前のメンバを
持つことがあるので、常に明示的に指定するのが自然ですが、
初期化の際は省略しても混乱は起きない、
といえば多少理由になるかな?
# {}を省略できなければならないわけではないが。
パッケージ化について、質問です。

知り合いからもらったパッケージのpacage.hを関数分けした、複数のCソースファイルで使いたいんですが、

<program01.c>
#include "pacage.h"

<program02.c>
#include "pacage.h"

とすと↓だいたいこんな感じのエラーがでてしまいます。
program02.obj : error LNK2005: "int (__cdecl* Funct01)(int) はすでに program01.obj で定義されています
program01内で、全部"pacage.hに定義された関数を使う分にはエラーでないんですが、プログラムが長いのでどうしても関数分けしたんですがどうしたらいいですか?

<pacage.h>
#ifndef _PACAGE_
#define _PACAGE_

typedef int (*FUNC01)(int,int *);
FUNC01 Func01;

#end if

>>300
>>300
エラーの原因は同じ変数が二度定義されているから。
解決策1:定義はprogram01.cで行う。
解決策2:条件コンパイルを使って何とかする。
pacage.hの
FUNC01 Func01;

extern FUNC01 Func01;
に変えて、program01.c内に
FUNC01 Func01;
を書く。
303300:04/01/20 14:05
>>302
ありがどう神様。でぎマじだぁ” (T-T)v

ところで、>>300
<program1>
#include "pacage.h"
FUNC01 Func01;
<program2>で
#include "pacage.h"
FUNC01 Func01;

としなくても、エラーでなかったんですが、これは↑寧ろ間違い?
>>303
#includeはファイルをそのまま取り込んでるので、そのようにすると、
>>300の状況と何も変わらんわけだが。
305294:04/01/20 14:08
>>299
>アクセスの時には、中身の構造体が外のメンバと同じ名前のメンバを
>持つことがあるので、常に明示的に指定するのが自然ですが、
>初期化の際は省略しても混乱は起きない、
なるほど、初期化の際は {}をネストしなくても、コンパイラが、何処に
代入すべきか判断可能なので、省略可能であり、省略可能故、手間を省くために
{}のネストはやらない。しかしアクセスの際には、コンパイラが判断不能となる
可能性が起こる為に、明示化が必要となる訳ですね。
納得しました。どうもありがとうございました。
>>305
まあ、構造体の定義にしたがって書いた方が混乱せずにすむとは思いますが。
307デフォルトの名無しさん:04/01/20 14:19
質問です。次のようなスクリプトがあったとします。

(1,2,3)
(4,5,6,7)
(100,200,300,400,400)

このスクリプトはかっこで囲まれた範囲が一つの配列になっており、
数値はカンマで区切られています。配列の長さは任意ですが、最大10です。
これをsscanfなどで簡単に読み込みたいんですが、どうしたらいいでしょうか。
C (C++ などではなくて) でオブジェクト指向プログラミングしたいのですが、
なにか参考になる書籍/ドキュメントはあるでしょうか?
>>308
gtk
2項係数(n個の中からr個を選ぶ組み合わせの数)を、計算するC++プログラム
から、最大数との割合を、各々について求めよ。という問題なのですが、教えてくれませんか?
int a[10], count;
count = sscanf(buf,"(%d,%d,%d,%d,%d,%d,%d,%d,%d,%d)",
              a+0, a+1, a+3, a+4, a+5, a+6, a+7, a+8, a+9);
312デフォルトの名無しさん:04/01/20 16:47
ファイルから、一行ずつ読み込み(<>区切りの物を)
個別に配列に格納したいのですが、途中で落ちてしまいます…。

どなたか、ご指導ご鞭撻の程、よろしくお願い致します。

http://www1.linkclub.or.jp/~yon/haha/saru-img/saru0656.c

>>312
なにがやりたいのかわからん。
elem[i]はcharじゃないし。BUFF_SIZEとelemの大きさの整合性が取れてないし。
elemにはなにをいれたいの?
>>312
突込みどころが多すぎて全てを指摘するの無理だね。
結局、mylineload()内で定義してる elem[5][20]に<>区切りの文字列を格納したいんだろ?
でも、仮にこれが成功しても上位には何も返らんよ。auto変数は関数を抜けると無効になるからね。
上位で格納先を提供した方がいい。
>>312
多分こういうことかな。君はかなり精進が必要だな。

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#define FILE_NAME1 "thl.log"
#define MAX_WORD_LEN 5
// ------------------
//   文字列 分割
// ------------------
char* strsplit(char* str,const char* delimstr) {
    char* delim_point = strstr(str, delimstr);
    const size_t delim_len = strlen(delimstr);

    if (delim_point) {
        *delim_point = '\0';
        delim_point += delim_len;
    }
    return delim_point;
}
316313:04/01/20 18:17
つづき
改行がおおすぎるとか待てとかいろいろ引っかかるなぁ。

// ------------------
// ファイル読み込み後
// ------------------
// return value: 読み取った word の数
int mylineload (char elem[][MAX_WORD_LEN], int maxwnum, char* buff) {
char* e_head = buff;
char* next;
int i;
for (i = 0; (next = strsplit (e_head, "<>")) && i < maxwnum ; ++i) {
snprintf(elem[i], MAX_WORD_LEN, e_head);
e_head = next;
}
return i;
}
317313:04/01/20 18:17
//----------------
//      Main
//----------------
int main() {
int max_word_num = 20;
int max_line_len = max_word_num * MAX_WORD_LEN;
char buff[max_line_len];
// Using 2-D array is the original poster's requirement :-(
char elem[max_word_num][MAX_WORD_LEN];
FILE *fp;
if(!(fp = fopen(FILE_NAME1, "r"))) {
fprintf(stderr,"File Open Error\n");
exit(1);
}
rewind(fp);
while (fgets(buff, max_line_len, fp)) {
int wnum = mylineload(elem, max_word_num, buff);
// debug output
for (int i = 0; i < wnum; ++i ) {
printf("%s ", elem[i]);
}
printf("\n");
}
if (!feof(fp))exit(2);
return 0;
}
318From:313 :04/01/20 18:19
しかもtab -> spaceしわすれた  _|^|o
319313:04/01/20 18:23
ごめんバグってるわ。自分でなおせるとおもうけど。
>>308
X Toolkit Intrinsics
>>310
宿題は宿題スレへ。
322312:04/01/20 20:30
>>313-319

> なにがやりたいのかわからん。

CGIでC勉強しようと思い、3日間、本とmanページ片手に試行錯誤です。
最終的に掲示板(perl)をCにしようと考えているんですが、
変数の型とポインタでつまずいてます。

> elem[i]はcharじゃないし。BUFF_SIZEとelemの大きさの整合性が取れてないし。
> auto変数は関数を抜けると無効になるからね。
> 上位で格納先を提供した方がいい。

ご指摘ありがとうございます。

> 多分こういうことかな。君はかなり精進が必要だな。

ありがとうございます。もう少し試行錯誤してみます。
>>312
俺の場合再帰関数つかうな。
void strsplit(char const* s, char* out)
{
  const char *p;
  while(*s != '<' && *s != '\0') ++s;
  if(*s != '\0') p = ++s;
  while(*s != '>' && *s != '\0') ++s;
  if(*s == '>') while(p!=s) *out++ = *p++;
  else if(*s == '\0'){ *out = '\0'; return; }
  *out++ = '\n';
  split(s,out);
}
>split(s,out);
strsplit(s,out);の間違い
可変個引数の関数で float型のデータ操作がうまくいきません。
double型にされてしまいます、助けてください。
そういう仕様だからあきらめるべし
他に可変個に使えない型ってありますか?
long double , float が駄目っぽいんですけど・・。
>>327
char, short も int に拡張される。
クスコでか?
330デフォルトの名無しさん:04/01/20 21:24
>>327
long doubleがダメとははつみみだ。
では可変個で使えるのは int型とdouble型のみって割り切っちゃっていいですかね?
あ。アドレスは除く
long intも使えれば、long doubleや構造体も使えるが。
334312:04/01/20 21:41
出来た!出来た!読み込み後を関数しないで、
読み込みバッファを大きくしたら行けた!

スレ汚し、ごめんなさい…。
>>330

質問スレで質問者の発言を真に受けるなよ
>>334
それ偶然だよ。まぁ偶然でも動けばそれでいいならいいんだが…
>>333
それらは環境依存ですか?
それとも決まってるんですか?

構造体はそれ以降の問題なので・・
long long ago; でライディーンが作れるぞ
int **matrix
と宣言して、mallocで、二次元配列分のメモリーを用意したんですが、
メモリーイメージだと、
(0,0) ― (1,n)
  |    |
(n,0) ― (n,n)
のように、ごく一般的な代数幾何の行列となるようにメモリー確保してます。

関数 func(int *) にたいして、
func(matrix[1]);

と渡すとコンパイルはできるんですが、関数内部でこちらの、意図するように動作しません。
こちらの意図では、
[1][0]〜[1][n]に対して値が代入されると思っていたんですが・・・。
ちなみにfunc内の処理はブラックボックスで見ることできません。

現在は、一度、for(i=0;i<=n;i++) vector[i]=matrix[1][k];
とやって、func(vector)とすることで解決してます。このように、vectorを定義しないでmatrixをそのまま
使う方法をご教授くださいm(_ _)m


vector[i]=matrix[1][i];
の間違いです・・・スレ汚しスマソ
**は[][]じゃない。
*が[]と同じに見えるところに騙されたまま
2次元を始めると極めて高確率ではまる超有名な落とし穴だ。

**が指し示す先の指し示す先へと2つ先へ進む様子を、実際に絵で書いてみろ。
それのどこが2次元か、自分に小一時間問い詰めろ。

釘を刺しておくが、おまいはポインタを1つしか作っていないはず。
>>341
「二次元配列分のメモリーを用意したんですが、」
こう言っているあたり、そうだろうな。
よくわからないのですが、二次元分のメモリーを確保する関数が↓

#define NR_END 1
int **imatrix(long nrl, long nrh, long ncl, long nch)
/* allocate a int matrix with subscript range m[nrl..nrh][ncl..nch] */
{
long i, nrow=nrh-nrl+1,ncol=nch-ncl+1;
int **m;

/* allocate pointers to rows */
m=(int **) malloc((size_t)((nrow+NR_END)*sizeof(int*)));
if (!m) nrerror("allocation failure 1 in matrix()");
m += NR_END;
m -= nrl;


/* allocate rows and set pointers to them */
m[nrl]=(int *) malloc((size_t)((nrow*ncol+NR_END)*sizeof(int)));
if (!m[nrl]) nrerror("allocation failure 2 in matrix()");
m[nrl] += NR_END;
m[nrl] -= ncl;

for(i=nrl+1;i<=nrh;i++) m[i]=m[i-1]+ncol;

/* return pointer to array of pointers to rows */
return m;
}

これは、とある本のルーチンをそのまま使ってます。
int **matrix;
matrix=imatrix(0,n,0,n);
344デフォルトの名無しさん:04/01/20 23:29
>>343
(詳しくは見ていないけど)領域の確保はしているみたいだね。
funcの使い方に問題があるんじゃないの?
m[

おまえはもう死んでいる
はぁ・・・だれかお願い。
意図するように動作しないなら、現在どう動作するのか、どう動作してほしいのかくらい書こうよ。
>>347
int func(int *)
引数にint vector[50]を渡すと、func内で配列に値が帰ってきます。正常に値がはいると、vector[0]には1が、そうでない場合は、-1が返ってきます。
仕様どうりに、funcにvectorをわたして、正常1が返ってくるので、それを>>343に挙げたルーチンで確保したmatrix値を代入して、プログラム全体が正常動作してます。
ところが、func(matrix[i]);とすると、matrix[i][0]に-1が返ってきてしまいます。なぜ・・・・。
>>348
NR_ENDが1になってるのが激しく気になるが、
この関数まさか1から始まる配列をつくるんじゃないよな?
ってゆーかさ、func() が渡された配列(?)のサイズをどうやって知るのかと。
351デフォルトの名無しさん:04/01/21 00:33
strcpyとか、mallocとか、色々関数がありますが、
これらの標準の関数を、自前の関数で上書きできますか?

strcpy()という、まんま同じ名前の自前の関数を作って、
str.libなんていうライブラリを作ったのですが、
標準のライブラリよりも先にそのライブラリを参照させるようにすれば、
自前の関数の方を通ってくれると聞いたのですが、
実際うまくいかないのです。

もともとのソースには手を加えられないので、
同じ関数を作ったのですが、自前の関数の方を通らせる事は可能でしょうか?
>>349
m[nrl..nrh][ncl..nch] だから
そのあたりは大丈夫だと思うけど...。
>>351
C++ なら名前空間で何とかなるけど、
C なら素直に名前変えれ。
354339:04/01/21 00:38
もう少し、正確に書くと。
int func(int, int *);

--------↓これだとエラー処理へいっちゃう。
int **matrix;
matrix=imatrix(0,4,0,50);
for(i=1;i<=4;i++){
func(i ,matrix[i]);
if(matrix[i][0]==-1){return;}//エラー処理
}

---------現在正常動作を得るためにこうしてる↓-------
int **matrix;
int vector[50];
matirx=imatrix(0,4,0,50);

for(i=1;i<=4;i++){
func( i, vector);
  for( k=0;k<=50;k++){
   matrix[i][k]=vector[k];
  }
  if(matrix[i][0]==-1){return -1;}//エラー処理
}

imatrix(a,b,c,d)に関しては、>>343

ほぅ

int vector[50];
:
  for( k=0;k<=50;k++){

正常に動作するのか。
356デフォルトの名無しさん:04/01/21 00:43
>>353
ウッ。。。
そうしたいのは山々なのですが、
もともとのソースに手を加えられないので、
なんとかならないかと思いまして・・・。

C++でも構わないのですが、方法は無いものでしょうか?
あーまちがえた、50ってしたら配列こえちゃう。。
じっさいは、ivectorってメモリー確保する同様の関数があって、
int *vector;
vector=ivector(0,50);
ってちゃんと確保してます。そんで、func( i, vector)をわたしてます。
int *ivector(long nl, long nh)
/* allocate an int vector with subscript range v[nl..nh] */
{
int *v;

v=(int *)malloc((size_t) ((nh-nl+1+NR_END)*sizeof(int)));
if (!v) nrerror("allocation failure in ivector()");
return v-nl+NR_END;
}
結局、そのfuncが、渡されたポインタが[0..size]ではなく、
[ncl..nch]であることは知っているのか、という問題だろ。
>>359
でも、>>357-358で渡したvectorに関しては正常動作してます。
ivectorも[nl,nh]だし・・・。
>>356
あー、やりたいことが分かった。
それはかなり難しい予感...。
リンカのオプションでそういうのがあればいいんだけど。

ソースをいじれないってのは、
#define strcpy strcpy2
というのを入れることすらできないってこと?
オブジェクトファイルしか提供されてないとか?
>>343
スマンが、その関数って誰の自作?
いくら何でも本に載せる代物じゃないよ。

二次元の分のメモリは確保されていません。
ポインタの配列に相当する領域を確保して、そのポインタの配列に対して
m += NR_END;
m -= nrl;
ってポインタ演算してます。
そしてポインタ演算されてズレたmの配列に
m[nrl]=(int *) malloc(...

これってそのポインタの配列のnrl番目のポインタに
nrow*ncol+NR_END個のintの領域を確保してるだけ。

絶対に、本に載るルーチンじゃないって。
363デフォルトの名無しさん:04/01/21 01:02
>>361
リンカのオプションですか。
調べてみます。

仰るとおり、元のソースはまったく触る事が出来ない状態です。
ソースはありますが、それに手をつけることは許されていない状況なのです。
どうにかできないかと思って。。。
>>362
ここを見ろ >for(i=nrl+1;i<=nrh;i++) m[i]=m[i-1]+ncol;

あと、これ Numerical Recipes in C だろ?
>>361
dllで提供されてます。中身不明。関数の仕様だけしかわからんです。

>>362
『Numerical Recipes in C』(4757円)という本があって、
数学的な関数ルーチンを提供してます。たとえば、FFTとか。
一個一個のルーチンは、世界中の数学者のうちのだれかが作ったものです。
>>364
それってポインタの配列の
ポインタをズラしてるだけじゃん。

断じて、領域確保なんかされてない。
どのCだろうが、ソースも読めないのか…
>>363
src ディレクトリにソースを置いて、

/* foo.c */
#define strcpy strcpy2
#include "src/foo.c"

という風にしてコンパイルするとかどうよ?
これならソース触ってない。
まぁ、これも許されてないのかもしれないけど。
おお、その本もってるな。
ページを載せてみてよ、読んであげるから。
>>368
ページって??
メモリー確保関係がかかれいるのは、P35
で、結論からいくと、メモリー確保されていないということでFA?
いや、>366はあふぉ
372デフォルトの名無しさん:04/01/21 01:17
>>367
なるほどー。
試してみます。
元のソースを触らなければ良いので、ちょっと試してみます。

>>365
宛先間違ってますよ。
>>366
ポインタ配列の領域を確保して、
二次元配列の領域全体をガバッと確保して、
あとはポインタ配列に
各行(row)の先頭アドレスを代入していってる。

各行を律儀に確保するコストをケチる方法として
よく使われるものだと思うけど。
0 オリジン限定じゃなくて、nrl, ncl オリジンにしてるから
かなり読みにくくなってるけど、
特に間違ってるようには見えない。
>>339

通常のcharの一次元配列を二次元配列のように扱うことができるのは確かだが、
こういう場合に、「char配列の先頭ポインタは文字列全体をハンドルする」という
規則が使えるだろうか?

この関数は、ばらばらに確保したcharの領域「を示すポインタ」を整列しているに過ぎない。

こういうことをやってみるとすぐわかる。

int main()
{
  int **s=imatrix(0,50,0,50);

  for (int i=0;i<50;i++){
   for (int j=0;j<50;j++){
    s[j][i]=j+i;
    cout << s[j][i];
   }
   cout <<endl;
  }

  for(i=0;i<(50*50);i++) cout <<s[i];

  return 0;
}
? 意味不明
やっぱ、君の自作?
俺のその本には、343の関数はのってないし
343の処理の説明もない。

float a[13][9]

float **aaにfloat*型で確保してコピーしてる説明が載ってるが?
>>376
いや, 本にはのってないけど, ソースにはある.
>>376
P35 から行列の解説があって、
P36 に imatrix のプロパティと、
付録 D に実装が書いてあることが示されている。
で、P658 に実装が載ってる。
プロパティ→プロトタイプだった...。
>>376
このメモリー確保する関数は自作してないですよ?
これはNumerical Recipesの全ルーチンを大学が買ったもので、
どっかからダウンロードしたか、送られてきたか・・・。
それをコピペして使ってる・・・。
>>354
>--------↓これだとエラー処理へいっちゃう。
>int **matrix;
>matrix=imatrix(0,4,0,50);
>for(i=1;i<=4;i++){
>func(i ,matrix[i]);
>if(matrix[i][0]==-1){return;}//エラー処理
>}

このforループの所は正確かな? func(i ,matrix[i]); iが2回あるのが激しく気になる
382デフォルトの名無しさん:04/01/21 01:27
>>367
ああ・・・だめだったんでした。
自作strcpy()の中で、strcpy()も使用しているため、
#define strcpy strcpy2
としてしまうと、strcpy2の中で使用しているstrcpyが使えなく
なってしまうのでした。

うぐぐぐ・・・。すみません。
>>382 ぎゃぐ?
>>382
自作 strcpy のソースでは
#define しなけりゃええんでない?
要は、本には二次元配列を止めてポインタの配列を使おうって言ってる。
これの違いを分ってないのが問題。
>>381
激しく func(50, matrix[i]); の予感。
>>381
func(int , int *)のことですか?
そのまんまで、あってます。
func
i 番の●●から、情報vectorを得るというようなルーチン。
i=1〜4の●●から、vector1〜4が欲しい。
といったプログラムです。
結局 Numerical Recipes では, >>343 で確保された行列を
(a[i][j] みたいに) そのまま添字つきでしかアクセスしないので,
double **a = (double**)malloc(sizeof(double*) * (N + 1));
for(int i = 1; i <= N; i++) a[i] = (double*)malloc(sizeof(double) * (N + 1));
で十分代用できると思うんだけど ...
全部のソースを見たわけじゃないから自信はないが.
って, もとの質問は何だったっけ.
わかりにくいかーw

えっと、噛み砕くと、 画像が4枚あって、ある画像にたいしてfuncの処理が行われると、vectorという情報が返ってきます。
matrix[1〜4][vector]に全部の情報を一括して格納したいってのがこのプログラムの目的です。
>>389
なら func(i, matrix[i]); で合ってる、ということか。
返ってくる情報の長さは 50 で固定なわけね?
どうも、matrix を色んな所で操作しているうちに
メモリ破壊が起きてしまって
エラーが出てるような気もしなくもないな。
392339:04/01/21 01:39
元の質問は、>>354
のプログラムがなぜエラーになるのか。です。
393339:04/01/21 01:41
>>390
固定とうか、実際は、40ぐらいでまでしか値は入らないです。
funcの仕様で、多めにとるようにと書かれていたので50にしてます。
だから、本も読めない奴の戯言は十分だっつーの。
本には、0offsetと1offsetの問題を解決した物だと説明がある。
kは0から始まってるよな?君のルーチン。
>>393
何かいい加減な仕様だな。
最低限確保しないといけないサイズとか
明記(というか #define)されてないの?
>>394
imatrix(0,4,0,50);
for(i=1;i<=4;i++){
>>396
func( i, vector);
  for( k=0;k<=50;k++){
   matrix[i][k]=vector[k];
  }
>>391
それはないです。matrix確保して、funcに代入までの間に、matrixに一度も触れてないです。
で、funcから返ってきて、値をいじらず参照したら、funcはエラーを返してきたんです。
400デフォルトの名無しさん:04/01/21 01:50
>>384
元のソースには手を加えられないので困ってるのです。。。
>>351
が質問もとです。。
>>400
自作 strcpy までも「元のソース」に含まれてるの?
>>399
int vector[50];
for( k=0;k<=50;k++){
の問題と

0offsetと1offsetの問題は別、
1〜49と0〜49は違う。  
>>395
funcの仕様では、
は、41まで書き込む可能性があります。41以上の配列を確保してください。
という、仕様です。で、安全で、切がいい50確保しました。
404デフォルトの名無しさん:04/01/21 01:56
>>401
いえ。含まれていないです。
元のソースをのstrcpyを自作strcpyに置き換えるには
どうしたらよいでしょうか?という事です。
>>402
結局何を指摘したいのか分からん。

func(i, vector);
で vector[1] 〜 vector[50](実際はここまでではないらしいけど) に情報が、
vector[0] にエラーコードが入ってるというのなら、
0 〜 50 までをコピーするのは当然だと思うけど...。
2 つの話が錯綜してるのか ?
いよいよもとの問題が分からなくなったんだけど,
>>354 の上のソースが動かないのが問題 ?

>if(matrix[i][0]==-1){return;}//エラー処理
>}

matrix[i][0] は NRC では無効な領域じゃないの ?
で, >>343 の領域確保をやると, matrix[i][0] == matrix[i - 1][nch] に
なるのか ?
---------現在正常動作を得るためにこうしてる↓-------
int **matrix;
int *vector;
matirx=imatrix(0,4,0,50);
vector=ivector(0,50);

for(i=1;i<=4;i++){
func( i, vector);
  for( k=0;k<=50;k++){
   matrix[i][k]=vector[k];
  }
  if(matrix[i][0]==-1){return -1;}//エラー処理
}
これ正常動作してます。

matrix=imatrix(0,5,0,10);
for(i=0;i<=5;++i)
for(j=0; j<=10; ++j)
matrix[i][j]=i*100+j;

for(i=0;i<=5;++i){
for(j=0; j<=10; ++j)
printf("%d*%d=%d ", i,j,matrix[i][j]);
putchar('\n');
}

特に問題なかったがな
>>404
例えば

/* src/foo.c */
#include <string.h>
int main() {
 char str[128];
 printf("%s\n", strcpy(str, "A"));
 return 0;
}

とあるなら、

/* foo.c */
#define strcpy strcpy2
#include "src/foo.c"

/* str.c */
#include <stdio.h>
#include <string.h>
char* strcpy2(char* dst, const char* src) {
 fprintf(stderr "%p <- %s\n", dst, src);
 return strcpy(dst, src);
}

とすればいい。
だから、343の関数は
たしかに領域はm[0〜][0〜]でも使える物だが
m[1〜][1〜]で使う仕様になってるって話だ。

分ってて、"k=0"なのか?
>>406
imatrix(0,4,0,50);
という風に 0 オリジンで確保してるから
matrix[i][0] は有効でしょ?
offsetの問題は本を見る限り解決してるはずなんだけど〜

>>408
ココの方は、速攻で質問のprogramを実行する気力があるかたたちなんだとなと、ビックリw
>>410 意味がわからんな
領域確保してんだから問題ない
はー…

m[i][0]にエラーを入れて、m[1〜][1〜]で使う仕様だっつーの。
m[i][0]でコピーじゃエラーを上書きしてるだろ。
そらエラーにならんわ。
415339:04/01/21 02:08
>>410
もちろん分かってて0 offsetしてます。
使用目的に応じて、1 offset 0 offsetで、使い分けられるのがこのルーチンの利点だと思ってるんだけど。。
今回のプログラムではたまたまfuncの仕様の関係で、0 offsetしてます。
意味がわからん
v[0]にエラーが入ってるのをm[?][0]にコピーしてると思われ
なるほど! そういう仕様だったのか。
つまり、自作のfuncを晒せって事だ。
つまり?w
int **matrix;
matrix=imatrix(0,4,0,50);
for(i=1;i<=4;i++){
func(i ,matrix[i]);
if(matrix[i][0]==-1){return;}//エラー処理
}
をどうしたらよろしいでしょうか?
funcの実装を晒せ。
自作funcは他人の自作なんで中身わからんです。
dllだし。。
と言ってみるテスト。
>>404
同名の関数はobjにある方がlibより優先される。
リンカの実装にもよるけど、普通はこうなってるはず。

それで、自分で勝手にルーチン変えて処理は合ってるって?

いいかげんにしろよ…
いいかげんにして欲しければ
要領を得ない3行列レスばっかなのをやめれ。
結局のところ、
vector=ivector()
matrix=imatrix()

func(vector)とわたすのと、func(matrix[i])と渡すので何が違うのかと・・・
そこが知りたいのだけれど。
間違えた

3行列レス → 3行レス
お望み通り。
| m[][], の中身を, printfで |
| 表示位, してみて, 確かめたら |
| どう, なんだ, と言いたい |
そりゃごもっともな意見だな。
それが面倒で、質問したらもっと時間かかったといいたい・・w
だって、単純コンソールプルグラムじゃないんだもん。
デバッガも無いの?
432デフォルトの名無しさん:04/01/21 02:28
imatrixなんて使わずに

int matrix[5*51];

をつかえば?

そもそも、この関数は
func(int i, int array[])なのか
func(int i, int *array)なのか
どっちよ。

| 適当な, fileに, でも |
| なんでも, 出力, する |
| 事も, 出来ない, のか |
>>432
その2つは同じだ。
435432:04/01/21 02:33

func(int i, int *array) ←こっち

ちなみに、プログラムがメモリーいっぱいつかうので、途中でどんどん開放するために、imatrix使ってる。
そういうわけで、int matrix[5*51];
でも、いいけどなんかなー。
やヴぇ。名前のところまちがえた。
>>432
ってしたかった。
実装が分らないbブラックボックスの話は出来ないし、
なんの環境か知らないが、表示やfile吐き出し程度も
出来ない奴のfuncの説明なんて信用なんないな…

とりあえず、値をチェックは基本の基本。
めんどうとか言ってるし…
晒された情報からは vector=ivector(), matrix=imatrix() の
どちらを使っても同じように思えるけど.
file に書き出しぐらいできるわっw
速攻解決してくれるとおもったのと、
べつに正常に動作する方法もわかってるからわざわざやらんかったし、
たとえやったとして、
matrixにこちらの意図するように入らない状態だったらプログラムの今後の混乱につながるから避ける。
たとえば、添え字を1ずつずらしてfuncに渡さなきゃいけないとかだったら、プログラムが分かりずらくなる。
func( i, matrix[ i ] );
の中で
処理はmatrix[ i ][ ? ]なのに
自分のソースではmatrix[ i ][ 0 ]でアクセスしてるのが信用なんない。

で、0offsetと使い分け?自分で使い分けるのはいいが
funcは使い分ける仕様なのかと…
>>438
でしょ??
funcの中身でなんか、やらかしてるんかな?
だって v[] のときはOKじゃん
>>439
死ねよ、主旨が変わってるだろ。
funcの仕様も解って無く、”エラーで動かない”
で、自分の仕様じゃないと
”混乱につながるから避ける”
”プログラムが分かりずらくなる”

プログラムを理解してるのか?
Numerical Recipesのルーチンを有効利用してるだけ。
func作者は他人なのでNumerical Recipesのことなんか、まったく考慮してないとおもわれ・・。
Numericalは、他で使えまわせないルーチンなのか?
>>443
自分しか使わんプログラムなんで。
自分が分かりやすいように書くのがいいかと。
もう、このスレでの解決の道がたたれたようなので、ねりゅ。
だんだん、気持ち悪くなってきたので、fileにでも出力して実際どうなってるか見てみるは。
散々引っ張ったんだから, 原因が分かったらせめて報告くらいしろよ.
>>445
そんな事はどうでもいい。
問題は、仕様も知らないfuncを勝手に置き換えて
>>439の発言は房過ぎるだろ。
? func() には変更はないが
>>421
dllでヒープ領域のポインタ渡しってだいじょうぶなんだっけ?
451ヽ(´ー`)ノ:04/01/21 09:09
情報処理の資格なんか要らねーから、デバッグとテストの資格が欲しいと思う今日この頃。
>>450
多分Windows上でのことだと思うけど、
結論だけ言えば同じプロセスだからOK
>>343
各値の変更に printf() 文を入れて実行してみた。

m = malloc( /*略*/ ); --- m = 0x003407A8
m += NR_END; --- m = 0x003407AC
m -= nrl; --- m = 0x003407AC

m[nrl] = malloc( /*略*/ ); --- nrl = 0, m[nrl] = 0x00340810
m[nrl] += NR_END; --- nrl = 0, m[nrl] = 0x00340814
m[nrl] -= ncl; --- nrl = 0, m[nrl] = 0x00340814

m[i] = m[i-1] + ncol; --- i = 1, m[i] = 0x00340840, m[i-1] = 0x00340814, ncol = 11
m[i] = m[i-1] + ncol; --- i = 2, m[i] = 0x0034086C, m[i-1] = 0x00340840, ncol = 11
m[i] = m[i-1] + ncol; --- i = 3, m[i] = 0x00340898, m[i-1] = 0x0034086C, ncol = 11
m[i] = m[i-1] + ncol; --- i = 4, m[i] = 0x003408C4, m[i-1] = 0x00340898, ncol = 11
m[i] = m[i-1] + ncol; --- i = 5, m[i] = 0x003408F0, m[i-1] = 0x003408C4, ncol = 11
m[i] = m[i-1] + ncol; --- i = 6, m[i] = 0x0034091C, m[i-1] = 0x003408F0, ncol = 11
m[i] = m[i-1] + ncol; --- i = 7, m[i] = 0x00340948, m[i-1] = 0x0034091C, ncol = 11
m[i] = m[i-1] + ncol; --- i = 8, m[i] = 0x00340974, m[i-1] = 0x00340948, ncol = 11
m[i] = m[i-1] + ncol; --- i = 9, m[i] = 0x003409A0, m[i-1] = 0x00340974, ncol = 11
m[i] = m[i-1] + ncol; --- i = 10, m[i] = 0x003409CC, m[i-1] = 0x003409A0, ncol = 11

return m; --- m = 0x003407AC


# malloc() で確保した領域の値が書きつぶされているが、
# これでどうやって領域を開放する気?
# ちなみに、各演算結果は期待通りか?
454453:04/01/21 11:36
>>453
ちなみに、コールは「imatrix( 0, 10, 0, 10 );」と言う形だ。
ざっと読んだけど
func(i,matrix[i])と
func(i,vector)じゃさ
全く違うじゃん。
func(i,matrix[1])じゃないのかな、同じ意味になるのって。

そもそもvectorって言う変数はリニアな1次元配列でしょ。
この人が言う処理だと、
for(i=1;i<=4;i++)って3しかループ回してない。

vector[1] - vector[4]までしか処理してないか
勝手に40まで処理するなら
(vector+i)[0 - 40]ってバッファオーバーしてるか
0オリジンならfor(i=1;i<=4;i++)コレは何なんだってことになるな。
457339:04/01/21 12:59
散々ひっぱったので結果だけ
matrixは0で初期化したあと実行してます。

for(i=1;i<=4;i++)
i=0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 (略)
i=1 -1 31 11 35 19 0 0 0 0 0 0 0 0 (略)
i=2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 (略)
i=3 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 (略)
i=4 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 (略)
i=1;で、matrix[1][0]に-1が代入されたのでエラー処理でプログラムを終了させてますんで、i=1以降は全部0

この結果は、matrxi[1]はmatrix[1][0]=-1以外の数値は正しいものです。
ただ、funcは、この処理において正しい結果を得られなかったとして、matrix[1][0]=-1を返してきました。

vectorをわたしたなら、1 31 11 35 19 0 0 0 0 0 0 0 0 (略)
と返ってきます。

>>455
>for(i=1;i<=4;i++)って3しかループ回してない。
1〜4までしか必要ないからです。というか、funcの書式(int a,int *v )の一つ目の引数が1〜4の値でなければならない仕様です。
matrix[i+1]を渡すより、添え字を揃えてmatrix[i]とした方が理解しやすいのと、プログラム全体に渡ってそういう書式で揃えてるので。
というか、本質的な問題でもなんでもない。
>>456
int *ivector(long nl, long nh){
int *v=(int *)malloc((size_t) ((nh-nl+1+NR_END)*sizeof(int)));
return v-nl+NR_END;}
なんで, >>426 の通りにやってるんだとすると, 同じ結果になるような気がするが ...
int func(int a, int *v) の仕様を示します。
何のプログラムを作っているか、言いたくないので
分かりやすくするためfuncは画像処理を行うものと考えてください。

[引数]
a その画像のどの位置に対して処理するか。 1〜4 (←画像が四分割されている)
v その位置の画像情報を受け取るためのint配列を指すポインタ

[返り値]
0〜 (情報A)

v[0〜]には以下の値が返る。
[0] 情報B(≧1)が入る。-1の時、画像処理に失敗(エラー)
[1〜n] 情報Cが入る。

C言語では文字列は、「文字の配列」として変数に格納される って本当ですか?
で、結論からいうと、情報Cは、得たい結果が得られているが、情報Bは得られていない。

>>460
そうじゃないと思いますか?
matrix=imatrix(0,4,0,50);

matrix=imatrix(1,4,1,50);
にしてみれば。
#define NR_END 1
の意味は、要素OffSetが1である前提の為のものに見えるんだが…
だから、forでは"i=1"スタートなんじゃないのかな。

imatrix内では確保は成功してるが、
各種ポインタ演算や最後のforで
割り当てがメチャクチャになってる様に見える。
464デフォルトの名無しさん:04/01/21 14:13
double func(double a,b){
double seq;
seq=a*b;
if(abs(seq)!=0) log10(seq);
else seq=1;

return seq;
};

borland C++ 5.5(free)でコンパイルして実行するとなぜかlog10のエラーが出ることがあります。
おそらくa*bがpow(10,-300)以下くらいになるとエラーがでます。
ちゃんとlog10(0)を計算しないようにしているのに・・・ 。
0と認識されていないのにlog(0)と同じように扱われるのです。対処方法とかないですか?
char(文字)で宣言してるから、でしょうか?
そう言われれば、そうかと思いますが…。

例えば、
int hoge [256];          // この一次元配列を 文字列の配列にするならば、
char hoge[文字の長さ][256]; // という多次元配列になる?

部分的に大きいデータが入る場合は、
全体的に大きな領域を確保しないとならない?

ゔ〜ん…
>>464
if(abs(seq)>0)

>>465
>int hoge [256];// この一次元配列を 文字列の配列にするならば、
atoi()ではいかんの?
>>466
すみません。概念が理解出来ていないんですよ。
今、必死で参考書読んでいるんですが…
468デフォルトの名無しさん:04/01/21 14:43
共用体の存在意義って何ですか???

構造体ならレコード形式のデータ格納その他の処理に使えるけど、
共用体って、メンバデータ全てで、同じメモリを共用する即ち
データそのものは1メンバだけしか扱えず、それを複数のメンバみたいに
扱うって主旨らしいんだけど。例えば32ビットの同じデータを32ビット
全部で扱ったり、8ビットずつ扱ったり、1ビットずつ扱ったりって、
参考書に書いてあるビットテスタ以外になんか使い道有るんですか???
>>463
imatrixといルーチンは、Numerical Recipesとう科学計算ルーチンが集められた本に書かれている。
この本では、その説明部分に以下のような記述がる。

『アルゴリズムによっては、0オフセットの方が都合が良いこともあるし、1オフセットの方が都合がよい事もある。
〜(略)〜付録Dに任意オフセット・任意長のベクトルを確保する次の関数が含まれている。
int *vector(long nl, long nh)
有効範囲[nl .. nh]の任意型のベクトルを確保する。』

このルーチンの便利なところは、例えば、Cの0オリジンであらわすところは、
int a[4];
とすれば、配列要素に扱う添え字は、0〜3 数学では、int a[4] で定義したら添え字を1〜4で扱った方が理解しやすい。
そこで、
int *a;
a=ivector(1,4);
で指定すれば、a[1]〜a[4]の添え字で扱える。a[0]にはアクセスしてはいけない。
つまり、int a[4]の宣言をみて、添え字をi+1で理解するのではなく, a=ivector(1,4)を宣言と見ることができるのが利点。
これは、a=(0,3)とすれば、int a[4]と同じメモリーイメージになるようにアルゴリズムされている。
今回、問題になっているプログラムでは matrix(0,4,0,50)としているので、5*51のメモリーを確保している。
int matrxi[4][50]で、定義して扱うのとなんら変わらない。

>>358の方が理解しやすいとおもう。
>>468
まさしく、メモリ領域を共用することが、存在意義なんだけどな。
正確には、メモリーイメージが違うけど。
今ではあまり使わんのかも。structの共用体とか
>>469
任意オフセットを使用したいなら、
任意オフセット分大きい配列を確保するだけに止めるべき。

元々確保した領域の先頭ポインタを残しておけば、
free() する時も頭を使わなくてすむし。


あと、本に書いている事が全て正しいと思うのはよくないよ。
>>469
自分で343のコードを確かめたの?
OffSetが0だと
>m += NR_END;
>m[nrl] += NR_END;
のポインタ演算でポインタがズレるアルゴリズムでしょ?
OffSetが1の前提の関数にしか見えないんだけど?

どっから、任意OffSetなんて出てきたの?
>>358を見た限りだと、

int v[4];だとすると、
v[0]のアドレスから、[0, 1 , 2 , 3]の4つの領域が確保される。

v=ivector(0,3)とすると、
確保される領域は、 [0][1][2][3][4]の5つ ←1つ多く確保される。
返されるアドレスは
[0] [1] [2] [3] [4]
  ↑ここが、v[0]

任意のオフセット、例えばoffset 2にすると、

v=ivector(2,6);
[0][1][2][3][4]が確保されて、
返されるアドレスは、
[-1] [0] [1] [2] [3] [4]

v[0] v[1] v[2] v[3] v[4] v[5] v[6]
使えるメモリーは、v[1〜5]でv[6]は使えないから、任意ではないな。
ただ、0と1は、任意に選べることがわかるな。
matrixの方もみてないからわからないけど、
おそらく、0 offet, 1 offset は、任意に選べるっぽいね。
これは、NR_END 1 で1つ多く領域を確保してるからだろうね。
NR_END 2 にしたら、2 offsetが使える。ある意味では任意といえるが・・w
>使えるメモリーは、v[1〜5]でv[6]は使えないから、任意ではないな。

v[1〜4] でv[5] v[6]は使えないの間違い。
>>475
なぜ"ivector"なの?
そんなのコード見れば、多く確保してるんだから理解出きるでしょ?
問題は"imatrix"
>>343
を読んで任意にポインタが展開されるか説明してみろ。
OffSetが1でしか、"目的の確保"は出来ない仕様にしか見えない。
明らかにOffSet0じゃズレるでしょ。
>>477
論より証拠でやってみたらいいんでないの?
どっかに0オフセット使って問題なかったって実効結果なかったっけ?
>>478
だから確保は出来るんだよ。
問題は、その確保した領域が
int m[4][50];
int **matrix = imatrix(0,4,0,50);

m[0][0] != matrix[0][0]
だって事。
で問題のfuncが、
ただ単にリニアにメモリ配置された2重配列を渡す仕様の関数だったら
ivectorで確保した物を渡しても動くが
imatrixで求めた変数のポインタでは動かないじゃないの?って話。
>>479
>m[0][0] != matrix[0][0]
>だって事。
ってどういうこと ?
おれには ivector と imatrix で同じように見えるんだけどなあ.
なんか見落としてるのかなあ.
すみません、初心者なのですが、どこで聞いていいのか分からないのでここに書き込ませてもらいます。

K&Rを読みながらやっているんですが、

 while(getchar() != EOF)

という条件のループを実際に動かしたときに
ループを抜けるコマンドが分かりません。
仕方なく getchar() != 'Q' などのように置き換えて進めていますが
気になっています。

よろしくお願いします。
479
は、メモリーイメージが配列とポインタでリニアと非リニアのことがいいたいんだと思うのだけれど、
配列の場合リニアだからね。
ただ、今回問題になっている、関数はfunc(int , int *)←
まったく、matrix=imatrix(0,4,0,50)で確保した配列をfunc(i,matrix[i])と渡しているので問題ない。
matrix[i]の指し示すアドレスにはリニアで、vector=ivector(0,50)と同じように並んでる。

この二つに違いはないはず。
>>481
while((c = getchar()) != EOF) {
    if (c == 'Q') {
        printf("Quit\n");
        break;
    }
    ...
}
>>481
Ctl-Zで抜けない?
>>481
DOS/WindowsならEOFはCtrl+z
UNIX系ならCtrl+d
486483:04/01/21 20:53
>>484-485
そういう意味だったのか…
487481:04/01/21 21:03
>>482-484さん
迅速な返答ありがとうございます。
Ctrl+z で抜け出せることも確認してきました。
どうもありがとうございました。

>>482さん
分かりにくい質問の仕方で申し訳ありませんでした。
どうすればEOFになるか分からなかったんです。
環境がDOS/Windowsだと付け加えておくべきでした。
488>>432:04/01/21 21:54
結局、func()の引数リストの問題じゃないかと。
matrix[n]は先頭アドレスを参照しているだけで、本体のアドレスはあくまでも別の場所だと
いうことがわかる。
下のソース試してみて。指定のところの&をつけたのととったので比べると違いがわかる。
int main()
{
int y,x;
unsigned int address;

puts("imatrix()を使った場合\n");

int **d=imatrix(0,5,0,10);
for (y=0;y<=5;y++){
address=(unsigned int)(&d[y])/ (sizeof(int*));       //ここの&をとると同じ
cout << "a["<<y<<"]のaddress: "<<address << endl;
for (x=0;x<=10;x++){
d[y][x]=x+y;
cout << x << ":" << y<< " :: "<< d[y][x] << " : * ";
address=(unsigned int)(&d[y][x])/ (sizeof(int));
cout << address << endl;
}
}
つづく
489>>432:04/01/21 21:55
つづき

puts("\n静的配列を使った場合\n");

int s[6][11];
for (y=0;y<=5;y++){
address=(unsigned int)(&s[y])/ (sizeof(int*));       //ここの&をとると同じ
cout << "a["<<y<<"]のaddress: "<<address << endl;
for (x=0;x<=10;x++){
s[y][x]=x+y;
cout << x << ":" << y<< " :: "<< s[y][x] << " : * ";
address=(unsigned int)(&s[y][x])/ (sizeof(int));
cout << address << endl;
}
}
return 0;

}
いかん、432はオレじゃないか。

要するに、この関数で取得した領域は一次元の添字でアクセスすると
参照をつかって配列の先頭アドレスを返すけれど、
そのポインタはまったく違うところに実体をもっているので、
プログラム内でm[0]に添字を使わないで何らかの判定をして
蹴ってしまうところがあったりすると、誤動作する可能性があるわけだ。
>プログラム内
ごめん、dll内のルーチンのことね。

>>468
union {
struct T {
int r1;
unsigned r2;
} s;
unsigned char c[sizeof(struct T)];
} u;
とでもしておいてロジック内部ではu.sを利用、
ファイルかなにかとのI/Fにはu.cを利用するってのはしばしば使う。
493113:04/01/21 22:15
>>233
ありがとうございます。
この後、更に大文字を小文字に変換し、各アルファベットの出現頻度を
画面に表示するプログラムを作成したいんですが
どうすればいいか分かりませんか?
宿題丸投げは別スレへ
495113:04/01/21 23:06
>>494
うるせえよばーか。
答えられねぇヤツは黙ってろよタコ。
おまえの特徴をよく憶えておく
>>493
こないだ、どっかのスレにそのプログラム載ってたよ。

5年前ぐらい。
498113:04/01/21 23:31
>>495
この113は自分じゃありません。
あしからず。
499デフォルトの名無しさん:04/01/21 23:36
演算子のオーバーロードって、順番もちゃんとしないとマズイですか?

Point operator+=(Point x , Point y) { 演算子+=の定義 }

Point operator+(Point x , Point y) {
Point z=x;
z+=y;
return z; }

たとえばこんなふうに+の定義に+=を利用する場合に、
+=のほうを先に読み込むようにしないとマズイか?ということ。
それとも同じソースファイルに書いてあれば書く順番はどうでもいいかな?
Cでは演算子オーバーロードはできません。
C++なら、関数呼び出しと同じ事ですが。
>>499
スレ違いを承知で言わせてもらうと、
+=と+はまったく別の演算子だ。
順番もへったくれもない。
スレ違いとはいえまともな回答がでてないのは……。
クラスのメンバ関数はグローバル関数なんかと違って
宣言の順番に依存しないで先んじて呼び出しが書ける。
最終的にクラスの定義にきちんと宣言されてれば。
>>502
空気読めない技術ヲタ。

はい、次の質問は〜?
俺には>>500-501がまともに見える。
>>502 は正しいことを言ってるがな。
一つ言えることは、「>>499 試せばわかる。」だな。
>>505
スレ違いのことをゴチャゴチャ言うのは >>503 が言うように技術ヲタと変わらん。
508デフォルトの名無しさん:04/01/22 12:37
すみません質問させてください
最近はじめた初心者です
#include <stdio.h>
main()
{
int a;
int b;
int c;
int d;

a=4;
b=7;
c=2;
d=a+c*b;

printf("理論的には変数%dと%dは%dによる効果をもたらす\n",a,c,d);
}
でコンパイル出来ないんですがどうでしょう?どなたか原因わかる方
いらっしゃいますか?
509デフォルトの名無しさん:04/01/22 12:40
>>508
環境とエラーの内容さらせ
510デフォルトの名無しさん:04/01/22 12:44
>>509
環境はWindows2000でCygwin Bash Shellを使ってます。
$ gcc -o test.exe test.c
bash: gcc: command not found
って出ます。
ファイル名testです
511プログラミング:04/01/22 12:45
Wolframのセルオートマトンのシミュレーションを行うクラス
CA::CA(int r,int n);//規則番号r,格子数nで初期化
int CA::update(void);//状態を更新する
int CA::operator () (int k);//格子k の状態を返す

規則番号は0から255の整数で与えること。また、境界条件を設定できるメソッドを作成すること。

上の課題を解いてください。お願いします。
>>510
コンパイル以前の問題かと。
>>511
マルチ厳禁。
Cで文字列比較したいのですが、エラーが出ます。

char m;

 〜 諸々の処理 〜

if (m == "rgt") {
} else if (m == "fnd") {      // 検索
}


warning C4047: '==' : 指定された演算子を含む式で、間接参照が矛盾しています。
warning C4047: '==' : 指定された演算子を含む式で、間接参照が矛盾しています。

参考程度で良いので教えていただければ、ありがたいです…。
>>511
HELL: goto HELL;
>>513
strcmp
>>510
>$ gcc -o test.exe test.c
>bash: gcc: command not found

「コマンドが見つかりません」
こんな英語くらい嫁。
パスが通ってないんじゃないの?
>>508
どうコンパイルできないのかを示すため、
環境とエラーメッセージを書かないとこちらとしてもどうしようもない
我々はエスパーじゃないのですよ

とりあえず思いつく限り

mainの戻り値が無い
パスがとおってない
ファイルを保存するのを忘れている
ファイル名が間違っている
>>513
char m; ←これは単一の文字
文字の比較なら、m == 'C'
文字列の比較なら、strcmpでも使え。

>>513
「文字」と「文字列」を区別汁!
>>515様 >>518

ありがとうございます。
勉強してきます。
521508:04/01/22 13:16
すみません返答遅れました
もう一度原因の方を追求してみたいと思います
ありがとうございました
522デフォルトの名無しさん:04/01/22 14:20
2進数文字列を10進数数値に変換するプログラム
はどうかけばよいですか?
空前絶後のエンターテイナーである、ゆじゅねさんと
空前絶後の道化である、かとFらと
またその他大勢が奏でるシンフォニーは一体どこまで加速して
このスレにカタルシスそしてカタストロフィーをもたらすんだ?
もう天衣無縫、豪放磊落なゆじゅねさんに
臆病で偽善の代名詞であるかとFはどうのたまい死ぬ
のか、もうこのスレから目を離すことはできましぇん。
この決戦案外は、少しノスタルジーな僕そしてその他大勢を
遥かなる天へと誘うレクイエムなのかもしれましぇん。

by sister M
>>522
strtol
ゆじゅねさんはこれまで様々な闘いをしてきた。
(えいかを倒して土下座させたのは有名な話)
それに比べかとFはどうだ?逃げてばっかじゃないか。
これからも誤爆すると思うんで
いちいち謝るのはやめるよ。
527デフォルトの名無しさん:04/01/22 15:46
質問です。

int *p, i=0;
p=(int *)i;

if( (int)p == i) puts(" ∧_∧\n(´∀`)\n");
if( p == 0 ) puts(" ぬるぽ\n");

(1) pがヌルポインタになることは保証されますか?
(2) (int)p == i が真になることは保証されますか?
どちらも保証されない
529404:04/01/22 16:30
>>404
>>423
ありがとうございます。
元のソースをいじらずに、関数のうわっかぶせすることができました。

しかし、ひとつ疑問が残ったのですが、
Cでコンパイルすると問題ないのですが、
C++でコンパイルすると未定義の関数'strcpy2'を呼び出した。
と、エラーがでてしまうのですが、何故なんでしょうか?
プロトタイプ宣言も追加して、あれこれ試してみたのですが、
何故"未定義"なのかがわかりませんでした。
スレ違いですが、わかる方がいらしたらお教えください。
530デフォルトの名無しさん:04/01/22 16:38
大きい配列の初期化ってどうやるんでしょうか。

int array[3] = {0,0,0};

くらいなら簡単に出来ますけど、もっと大きな配列だとそうもいきません。
Perlみたいに最初から0が入ってて欲しいのですが
ループ回して入れてくとパフォーマンスが落るし
大きな配列の初期化ってどうやってるのでしょうか?
>529
extern "C"でも忘れたんじゃねーの。
>>530
0で初期化するなら
int array[1000000] = {0};
これでいいと思った。それかmemset使うとか?
C言語でUNIXの外部コマンドを使いたいんですがどのようにプログラムすればよいでしょうか?
例えば、CGIでwhoisコマンドの出力をさせるような感じです。

上手く表現できず申し訳ないのですが、どなたご教授をお願いします。
pipeのこと?
>>533
スレ違い。system使え。吐き出す内容をプログラムで受け取りたかったらpopen使え。
536533:04/01/22 16:56
レスありがとうございます。
知らないことばかりなので検索してきます...
ありがとうございました。
C言語とC++って何が違うんですか?
>>537
名称が違うだろ。
>>535
system も popen もヘタレだけがつかうもの。
pipe & fork & exec つかえ。
540527:04/01/22 17:17
>>528
解答、ありがとうございます。
どちらも、環境依存ということで理解しました。
>>532
要素不足の暗黙の初期化は0になるが、
memsetだと、ポインタとか浮動小数点の場合に保証されない。
>>539
無理すんなよ。
入力か出力のどっちかだけ必要な局面で
popen() 使ってなかったら、却って恥かくぞ。
> 無理すんなよ。

いみふめー
>>542
要は使い分けで、たとえば頑なにprintf族の関数を使わずにwriteだけで
何とかしようとするのはマヌケだというだけ。

popenで十分なときには使えばいいし十分でなければちゃんとやるだけの話。
自己満足で使ってる分には構わんけど、popenを使うやつは云々、
なんて言っちゃうのはとてもマヌケだと思うな。何のためのライブラリなんだと。
ここってこんなにトゲトゲしてたっけ?
546デフォルトの名無しさん:04/01/22 18:45
たまにこういう流れになりますね。
popenで十分ならpopen使うことに同意するが、
いちいちsh動かされたら十分じゃないことが多い気がする
>>545
最近は、ほんのすこしのズレも許せないというケツの穴のちいせぇ
奴が世間には増えた。

そのあおりを受けたんだろう。
549デフォルトの名無しさん:04/01/22 19:48
クラスと構造体の違いってなんですか?
>>549
C言語には(ry
>>549
構造体にメンバ関数を入れただけ。
使い方でいえば、構造体はレンタカーでクラスは運転手つきのタクシーだ。
>>551
うーん、そうかな。
C言語でも関数のポインタとか入れられるからな。
>>549
構造体っていうのはある集団をまとめて
1つの塊にしちゃえばなんとなく管理しやすいし
また、仲間だということが明確だから
そんな感じ。
クラスってのはある集団そして動きをまとめて
1つの塊にしちゃえってだけではなく初期化、終了動作
自動システムであるコンストラクタデストラクタなども
装備した完全なるクラス体系。
どっちがいいかと言われればまあ難しいのだが
Cでは構造体がよい。なぜならクラスをつくるには
関数化しなければならないから。C++ではクラスを
使うのがよい。なぜなら、クラスとは構造体と
上位互換を持っているからだ。
>>553
おいおい、マジか?
>>553は非常に的を得た適切な説明だ。
これまで、あやふやだったclassと構造体の
区別が今、>>553によって完全になされたと言っても
過言ではないように思う。
ネタだと言ってよ・・・
>>553
ここは初心者が見るのでマジレス。
でたらめ書くな。
>>557
では、あなたが説明したまえ。
>>555
>的を得た
なるほど、射掛けられちゃうのか。
「Cでは構造体がよい」ではなく、「Cにはクラスがない」のだから話にならないな。
じゃあ、本気になって議論してみようか。
まず構造体だが
struct hoge{
int a;
char *s;
}
こうだ!
ではクラスはどうか?
class hoge{
int a;
int b;
void f();
}
hoge::f(){
}

こうだ。
もうこれ以上の説明はいらないと思う。

562おしい:04/01/22 22:40
; が
>>555
C言語学ぶのは大いに結構だ。
でも日本語もしっかり勉強しろよ。
このスレで質問に答えて
得意そうに解説してる奴の大半は当てにならない。
構造体とクラスが殆ど同じと言ってる人は
オブジェクト指向言語は C++ しか知らない人。

構造体は本来単なるデータの集まりとしての意味合いしか持たない。

クラスはデータを直接見るのを(極力)やめて、
その操作のみを外部に公開してやることにより、
データを抽象化したもの。
>>565
そこに愛がなければ
すべては無意味だと思う。
>>565
だってCスレだもん。そして、C++では理念は別として、動作上はほとんど同じだからな。
一般論的な話は余所でやればいいし。
じゃぁ、愛も入れよう。
>>565
言ってくれるねえ
そりゃ俺は C++ 一筋の15年生さ
けっ
570557:04/01/22 23:14
>>558
では挑戦してみる。

> クラスと構造体の違いってなんですか?
言葉の定義でまず微妙な問題がある。ここの「クラス」、「構造体」
をC++の文法で定義されているものとしてのclass, structと解釈すると、
classはデフォルトがprivateだがstructはpublic、というぐらいの違いしかない
(重大な違いをみのがしてたら訂正宜しく)。
従ってほとんど同じ物である。
また、例えばC言語でstructと関数ポインタを利用してOOPをすることができる。

したがって、むしろここでは、 「クラス」と「構造体」との
概念上の違いを説明しようとするべきである。既に述べたように、
struct, classといった言語上の要素がどう利用されうる(可能)か
ということは、別の議論である。
一言でいうと、
構造体: いくつかのデータを一塊とみなしてまとめたもの。
クラス: いくつかのデータと手続き(関数)を一塊とみなしてまとめたもの。
上の短い説明はあいまいだしもちろん全てをつくしてもいない。正確に
理解するには、OO{A, D, P}の意図とメリットについて、学ぶ必要があり、
それゆえ掲示板で説明し尽くすのは不可能である。
ここでC++に戻ると、C++のclassはOO*のオブジェクトの
概念を反映し、データ抽象、継承などOOPの実現を容易にするように、
(現実的な妥協のもとで)設計された文法要素である。一方、structは上記
「構造体」を意識している。
どうでもいい。
漏れの考える理想のclassは↓こんなのかな。

class Hoge{
public:   //隠し事などいらない。
int a;
int b;
Hoge();
void print();
愛;   //心がすさみがちなプログラマにこそ愛は必要だと思う。
}
そして時は動き出す・・
おまいら、精神状態大丈夫か?
オレは女性オブジェクトへのポインタをいっぱい持っているのに、
オレのポインタを保持しているオブジェクトはきっと誰もいない。

オレは一人ぼっちだ。
free(575); /* C ってめんどくせ */
>>576
やっと開放されたよ。
僕を見つけてくれてありがとう。



本気で気が滅入るな、こういうの。
C言語をマスターしている人のためのC++の本・もしくはサイトないかな?
>>572
3-Bにでもいったら?
#include<stdio.h>
//DQNな質問で申し訳ない
void f(void);

typedef struct {
void (*a)(void);
}HMM;

void f(void){
int a,b;
a=3; b=2;
printf("%d\n",a*b);
}

void main(){
HMM seq;
seq.a=f;//こんなことわざわざしたくないCで何とかできないの?
seq.a();//いきなりこれを実行させたい
}
>>580
#include <stdio.h>
void f(void);
typedef struct { void (*a)(void); } HMM;
void HMM_Init(HMM* hmm) { hmm->a = f; }
void f(void) { printf("%d\n", 6); }
int main() {
 HMM seq;
 HMM_Init(&seq);
 seq.a();
 return 0;
}

初期化が静的な値の単純な代入のみなら、
HMM_Init を定数にしてもいい。

typedef struct { void (*a)(void); } HMM;
const HMM HMM_Init = { f };
int main() {
 HMM seq = HMM_Init;
 seq.a();
 return 0;
}
583デフォルトの名無しさん:04/01/23 08:58
>>581
ねぇねぇ、下はHMM seq={f};じゃダメなの?
>>583
マジックナンバーだからね。
それに、色んなところで { f } とすると
変数を増やしたときにややこしいので、
保守性を優先するなら使わない方がいい。
>>580
死ね糞マルチ
Cで、ファイルを幾つか操作するプログラムを書いているのですが
「run-time error R6000 - stack overflow」が出ます。
Googleで調べると、FDISKコマンドで出るとか関係のない話ばかり…。

(恐らく)バッファを確保する所で出ているのではないかと思いますが、
どなたか、対処法ご存じの方居られましたら御教授願います。

コンパイラは、Microsoft (R) C/C++ Optimizing Compiler Version 8.03です。
なんか、定期的に
・スタックオーバーフロー
・エスケープシーケンス
・ディレクトリ
・scanf

が出てくるよな。

誰か、(多少環境依存も含めて)2ch版FAQ作らんか?
言い出しっぺ
>>587
FAQというよりコピペ用回答集だろ?
FAQなんかつくっても誰も読みはしないだろうし。
>>586
それだけの情報だと一般的なことしかいえんよ。

・auto変数(staticでないローカル変数)で大きい配列を取ってないか
・再帰関数が暴走してないか

がよくあるスタック溢れの原因だ。

前者なら、とりあえずでかい配列にstaticをつけることで対処できる。
が、リエントラントでなくなるのでそのあたりは気をつけたほうがいい。
DLLなんかでその辺に気を使わないとはまる。

後者なら、ま、がんばってデバッグしてくれたまえ。

あとはリンカオプションでスタックサイズを増やすことができて、
それで対処できることもある。
>>582
どうも、ありがとうございます。(^o^)
MS-C8ってVC1.0?
とすると16bitだし、
確かDOSではデフォルトでスタック2Kとかしかないんじゃなかったっけ?
593デフォルトの名無しさん:04/01/23 20:20
LinuxでCを使用しているのですが、_msizeに変わる関数はありますか?
va_list list;
string s;

va_start(list, s.c_str()); ←コンパイルエラー

でコンパイルエラー「'&'に左辺値がありません」が出ます。
マクロの va_start() が何か悪さしてるんでしょうか?
なにがやりたいんだ?
>>594
どんなネタだ!?
#include<stdio.h>
int main(void){
printf("Good-bye world\n");
return 4;
}
mallocとか、newで動的にメモリー確保するときに、
必ず、ちゃんと確保されたか確かめるコードを入れますが,
確保されなかったとき、メモリーが足りなかったと判断してよいのでしょうか?
偶然的にアクセスしてはいけないメモリー領域に確保しようとすることはありえますか?
ありえない
600586:04/01/24 04:53
>>590
貴重な情報、ありがとうございます。
前者でした。

>>592
> MS-C8ってVC1.0?
Microsoft Visual C++ 1.53とか出てました。
中学生の時に買ったMS Visual C++ 95(?) Pro に付いてきた物です。

> とすると16bitだし、
> 確かDOSではデフォルトでスタック2Kとかしかないんじゃなかったっけ?

聞いた事があるかもしれません。
GCC3.2でコンパイルしてみるとエラーにならないから不思議でした。
>>600
VC++1.53はVC++4.2におまけで付いてきた奴だと思う。
間違いなく16bit。

せめてVC++4.2の方使えよ。
きれいなコードを書くために参考になる本があればお願いします。
まだ初心者なので、簡単なものを紹介していただければ嬉しいです。
603586:04/01/24 12:55
>>602
Cプログラミング診断室
http://www.pro.or.jp/~fuji/mybooks/cdiag/index.html

昨日、本屋で見かけたよ。
俺が見た時は無かったから、HTMLの全ページプリントアウトしたけど。


>>601
> せめてVC++4.2の方使えよ

コマンドラインからコンパイルしたいんですよ。
「** xx.c -o xx.exe -Wall -O3」みたいな形で。
コードヲーリアとか、コンパイラは複数入って居るんですけど、
binディレクトリ見つからないし、全コマンド調べるの大変なので、
身近にあって知っている物使いました。
605604:04/01/24 12:56
>>603
33 分も間が開いてるのにケコーンしてしまった。
VC++でコマンドラインコンパイラが使えないと思ってる奴もいるのか。
みなさんにも非常に興味深いと思われる質問
があったのですが、あなたたちに聞いてもどうやら
無駄のようですので、出すのは止めます。
良い心がけですね。興味がある人など一人もいないでしょうから。
ここにいるのは役に立たないクズばかりですね。
もういいです。
ハイハイ、わかったからもうこないでね。
クズだって燃えるんだよ。

612609:04/01/24 14:40
元ネタ知ってる人が1人や2人は居るだろうと期待してるんだけど・・・
ちなみに俺は607ではありません。
>>612
いい加減、寒いよ。
どうしようもないな
>>607=>>609は。
↑ネタですよね?
とまあ、ネタにマジレスする人を眺めるのが楽しいわけですよ。
なんか必死な人がいますね。
プログラマはcoolであれ、と云いますが。
まあ、それは釣りと呼ばれていて、マジレスする人は釣られたというだけのことなんですが。
釣られて、というより全部のエサに食いついて
必死な人がまだ居るんですね。
すまんな>>609
そもそも俺が>>607なんだよ。
釣られたのは君なんだよw
>>607なんて本気で相手にしてるのは>>608だけじゃん。
>>609には沢山レスがついてるみたいだけど。
>>623=>>609
もう見苦しいよ。わかったよ
君は最高の釣り師だ、すごいよ。
でももう来ないでねw
っていうか、誰が誰なのか全然わかんないんだけど。
書き込んでるのは>>622>>609だけか。
>>609に対するレスは全て>>607=>>623の自作自演って事ですね。
ていうか、釣っただの釣られただの言ってる奴、イタい。
DQN はラウンジにでも逝けよ。
>>627
ハゲドウ。
618 名前: デフォルトの名無しさん [sage] 投稿日: 04/01/24 14:56
とまあ、ネタにマジレスする人を眺めるのが楽しいわけですよ。

620 名前: デフォルトの名無しさん [sage] 投稿日: 04/01/24 15:00
まあ、それは釣りと呼ばれていて、マジレスする人は釣られたというだけのことなんですが。

↑なんか厨房くさい。
ま、週末だし。
多少は変な人が来るのも仕方ないでしょ。
ある関数の中で、例えば、
hoge = (double*)malloc( sizeof(double) * 1000000 );
等とメモリを確保して、
処理を続けていく上でよくない状態になったので
「良くない状態になりました」をあらわすコードと共にリターンして、
リターンした先ではそれ以上処理しないでプログラムを打ち切ることがわかっているとき、
「free(hoge)をしなくてもいいかなぁ」と思ったんですが、
プログラム終了後にゴミが残ったりしますか?
ふつうしません。
632630:04/01/24 18:00
>631、ありがとう御座いました。

「ふつうしません。」の「ふつう」なのが、
「ゴミが残らない」のか、「ゴミが残らないゆえにfree(hoge)をしない」のか
追加いただけると非常に助かるのですが。よろしくお願いします。
>>632
既に malloc() できている領域は確保されたままだが、

> リターンした先ではそれ以上処理しないでプログラムを打ち切ることがわかっているとき、

と言うことなら、ゴミが残ろうが知ったこっちゃないからわざわざ free() しない人もおおいだろ。

あんま突き詰めると戦争になるので、ほどほどにな。
634デフォルトの名無しさん:04/01/24 18:26
ある計算の高速化のためにCプログラムを改良するたびに
clock関数で時間を計っていたところ
clock関数で表示される時間は短くなったのですが、
実際にかかった時間(時計で計った時間)は遅くなってしまいました。
原因として何が考えられるのでしょうか?
分かる方教えてください。よろしくお願いします。
ちなみに使用しているOSはWindows XPです。
635デフォルトの名無しさん:04/01/24 18:36
関数って言うのは決まった処理を返してくれるから関数というと
聞いたんですがあってますか?
>>630
ゴミは残らない。OSが責任をもって回収する。
したがって無意味ですが、潔癖症な人はfreeをするでしょう。
>>635
違います。決まった「値」です。
例えば、sinはpiに対して常に決まった値0を返すので関数です。
処理(関数等)が値であるような言語では「決まった処理」をかえすことも
あります。
ここはC言語のスレだったということを忘れていたので。

本来関数とは>>637の意味ですが、
C言語やJava等、命令型の言語では、必ずしも同じ値を
返さないサブルーチン(例:getchar()等)も関数と呼びます。

関数型言語には、本来の意味の関数しかもたない言語も
あります(例:Haskell)。
639630==632:04/01/24 19:06
>633,>636、激しくありがとう御座いました。
ついでに、関数は値を返す以外に、副作用を伴う場合があり、その副作用の方が主の場合もあります。
>>640
本来それは関数ではないわけで…命令型言語的には「関数」だけど。
このスレで関数といえばCの関数なわけで・・・
>>642
>>635の質問に対する答えだということを忘れないように。
写像としての関数。
サブルーチンとしての関数。
これが漏れのイメージかな。
645デフォルトの名無しさん:04/01/24 21:37
「決まった処理を返してくれる」
なんていう言い方は、そもそもあまり使わないんじゃないか?
「決まった処理」は「実行する」と続けないと座りが悪い
初めて貴方を見た 恋のバ関数
なんだかスレがいい方向に流れてきましたね。
プログラマに必要なのは関数ではなく愛。
この私の主張がどうやら受け入れられてきたようです。
愛があればなんだってできますね。
例えば、素数を順に羅列するプログラムを書きたいとします。
その場合
まず愛型を定義します。
愛;
int main(void){
愛;
}

これだけですべての素数は羅列されることになります。
愛があればなんだってできる。漏れはそう思いますね。




愛があれば。。。こどもができる
愛がなくてもできるが(w
愛があっても金はできない。
愛は金になる。
金も愛になる
>>645
それは「処理」という言葉の捕らえ方の違いだけではないでしょうか。
言語によってはアルゴリズムというかメソッドを返すものもあります。
(関数ポインタに近い?)
おまいら、何かつらいことでもあったか?
つらい"こと"はない。つらいと"感じ"てるだけだ
655637:04/01/25 01:48
>>645
>>637では、(純粋)関数や、(monadic) actionを返す場合について書いた。
Cでいえば関数ポインタを返すことにあたる。
返したからといって実行するとはかぎらない。

>>635が「実行する」のつもりで「返してくれる」と書いていた
ということなら、ありえるね。しかし「決まった処理を実行する」
のは関数ではなくてサブルーチンだな。
小難しいことはいいよ。
C では関数ってのは処理をまとめたもので、
戻り値で何か結果を表す値を呼び出し元に返せるし、返さなくてもいい、
ってだけでいいんだよ。
Cに特化した話で十分。
>>655
signalなんかは関数のポインタを返してくるね。
標準関数だっけか? 忘れた。

呼ぶとは限らんけど。つか呼ばないか。
659デフォルトの名無しさん:04/01/25 12:19
C限定の話ではないんですけど、
ある整数xがある場合に、x以上で最小の2のべき乗を求める
すなわち、log2 x <= n
となる最小のnを求める速い方法はないでしょうか?
xの1となる最上位ビットを1ビット左シフトすればいいんでしょうが、
最上位ビットを演算で求める方法が思い浮かびません・・・
遅いものがるからこそ速いものがある。
速い遅いの基準がないんだけど。
>>659
うまい方法があるのかもしれないけど、普通にループ組んでも十分な速度は出ると思うよ。
>>659
C 限定じゃないなら
Intel 系 CPU には bsr なる命令が用意されていて、
これを使えば簡単に最上位ビットを求められる。
>>659
惜しいな。xの1となる最「下」位ビットを求める手法なら

x & -x; // 但し x は unsigned 型

という離れ業があるのだが。

誰かそんな手法を知っている香具師がいたら漏れにも教えてくれ。
664デフォルトの名無しさん:04/01/25 14:31
>>659
一応書いとくと
0になるまで右シフトして、その回数をカウントし、
2を累乗する
ぽいけど
>>663みたいに論理演算でやりたいよなあw
うぉ・・・すげー高度だ。
ここの住人は凄いな…。俺なんてビット演算なんて見ただけで吐き気がするんだが・・・。
プログラマーでもない一介の大学生の俺にビット演算って必要ですか?
中学のとき、2進数ですら混乱した俺が、16進数なんて扱えるとは到底思えん・・・。
CPUがギガレベルにまで達した現在、ビット演算って俺には、第三者にわかりづらくするだけなようにも思える。
でもなんかカコイイからマスターしたいな。

>CPUがギガレベルにまで達した現在
CPUがギガレベルにまで達した現在でも、コンピュータは2進数でしか動かないと思うんだけど…

>第三者にわかりづらくするだけなようにも思える。
微妙にズレてるが、言ってる事は、あながち間違いでもない。
暗号化とかビット演算使いまくりだし。
ビットフラグくらいは使えるようにならないとな、と。
>>666
>暗号化とかビット演算使いまくりだし。
それが、暗号の強度と関係あるのか?
圧縮もビット演算使うね。
670デフォルトの名無しさん:04/01/25 16:16
戻り値は

const char* function
char* function

const char*と、char*どちらがいいのでしょう?
goto スレからいらっしゃいましたかw
ええ、見事にするーされちゃったので
         / ̄ ̄\
        ( ^┏Д┓^)
         ゝ     く
           ∧_∧  |    ____________
        三  (    とノ  /
      三   /   つ | < ワ━━━━ッ!!!! ゆじゅねさん!!!
     三  _ ( _  /|  |   \
        (_ソ(_ソ(_ )     ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄
\__________  _____________/
                ○
                O  
                __
           ,―γ ___ヽー、
       | ̄ ̄|  | |(/),(ヽ)|    | ̄ ̄|
      |   ヽ  (6  ー  )  ノ    |
      -――  ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄――-
     |  ,―  ̄ ̄ ̄ ̄ ̄ ̄ ̄ ― 、    |
     |  |                |    |
     |  |                 |    |
    |  |                  |    |
   |  |                   |   |
>>670
状況による
ゆじゅねさんって知ってる?
最高に強い雀士なんだよ。
20年間無敗といわれた桜井に
唯一土をつけた男なんだ。
その影響力ははかりしれず
http://www2u.biglobe.ne.jp/~billy-hp/mfc/enqlog/enq03log.htm
ここでも1位にランクインされてるほど。
676659:04/01/25 16:41
>>660-664さん
いろいろ頭を使って頂いてありがとうございます。
何故か書き込みができなくて、レスが遅れてしまいました。

>>662
bsfもbsrも知っていますが、残念ながらx86系ではないので・・・

>>663
その方法は私も知っており、多用して、周りから変な目でよく見られます
>>664
そうなんです、
今は、
n = 0;
while (x) {
 n++;
 x >>= 1;
}
でやってるんですけどね、演算でできれば美しいなぁと思いまして・・・
677659:04/01/25 16:43
ネタついでに、プチテクとして、
変数xが2のべきであるかの判定方法
((x & (x - 1)) == 0)
>>659
> ある整数xがある場合に、x以上で最小の2のべき乗
って、0b1000 の時は 0b1000 で、0b1010 の時は 0b10000 ってこと?
>>676
C言語の範囲を逸脱しちゃうけど、ビットの並びを反転するレジスタはない?
そしたら>>663氏の方法を使ってこんなこともできそうだけど。

*REVERSE_BIT_REGISTER = x;
x = *REVERSE_BIT_REGISTER;
x &= -x
x >>= 1;
*REVERSE_BIT_REGISTER = x;
x = *REVERSE_BIT_REGISTER;

でも、周辺とI/Oしちゃうと本当に早いのかどうかわからなくなっちゃうね。
排他も必要になってくるし。
680659:04/01/25 16:52
>>678
そうです
>>679
そんなレジスタをもったプロセッサがあるんですか!?
まだまだ私も視野が狭いんですね・・・
トリッキーなコード その2
http://pc2.2ch.net/test/read.cgi/tech/1038215563/

こっちで話した方がいいかもね。
682663:04/01/25 17:23
>>676
>多用して、周りから変な目でよく見られます

いや、こんなの多用している奴は
俺でも変な目で見るぞ。
マクロにしてコメント付けとけば OK 。
684デフォルトの名無しさん:04/01/25 18:40
C言語でpasswordによるファイルのロックをしたいのですが、
排他制御だとソフト起動中しかロックできないので
またpasswordいれないと
半永久的にロックしているいい方法ってありませんか?
>>684
暗号化。
>>684
>半永久的にロックしているいい方法ってありませんか?

もし、そのプログラムが暴走した時、
一体どういう対応をとるつもりだ?
687^^:04/01/25 19:50
#include<stdio.h>

#define ORIG_STR "ymq\n"
#define CIPHERKEY 1

void cipher(unsigned char n, unsigned char *a)
{
while (*a !='0'){
*a=(unsigned char)(*a ^ n);
a++;
n++;
}
}

int main(void)
{
unsigned char a[4] = ORIG_STR;
unsigned char n=CIPHERKEY;

cipher(n,a);
printf("%s\n",a);
cipher(n,a);
printf("%s\n",a);
exit (0) ;
}プログラムを実行した結果は
xor
ymq
となりました。どうしたらこういう実行結果になるのですか?
ただし、英小文字をあらわすASCIIコードは、a〜zで16進数で61〜7Aです。
>>687
そういうふうになるから。
マルチポストはやめましょう。
689デフォルトの名無しさん:04/01/25 20:15
>>687
マルチなのもあれだから、
ソースを書いておいて、「どうしたら」はないだろ
dllをCで作成して、そのdll内でデータを入力するためにメモリーを動的に確保しました。
そのdllをUnloadした時に、そのメモリーを解放せず、再びそのdllが呼ばれたときに、
前回確保した同じメモリー領域とそこに記録されているデータにアクセスして読み出す方法はありますか?

ファイルにデータを入出力すれば同じことができますが、アクセス速度が落ちるので
メモリー上に記憶させておきたいのですが・・・どなたか、こういった場合の一般的な方法を教えてくださいm(_ _)m
>>690
環境依存かな。
呼び出し元が保持しておけばいいだけじゃないかと思いますが。
>>690(=>>684?)
変なこと考えるね。プロセスが終わったのにメモリが開放されない
OSなんてろくなもんじゃないと思うんだが。
>>690
メモリをファイルとして扱う VxD を作る。
694690:04/01/25 21:09
>>691さんの言うように呼び出し元でデータを保持しておけばいいわけですけど、
呼び出し元がVBなんで・・・ ←処理遅そう
全部Cで作ればいいことなんですけど・・・。そうですね・・う〜ん。

>>693さんのいうVxDなるものを知らなかったのでちょっと調べてみたらとても興味深い
ものですね。Cで作るのもいいけど、なんかこの方法を試してみたいです、
良い参考文献などあったら教えて下さい。難しいなら諦めますがw
処理遅そう≠処理遅い
>>690
アクセス速度はOSの問題として、割り切った方がいいと思うよ
頻繁にアクセスされるなら、キャッシュされるだろうし
リソースの解放の心配もいらない
>>693
管理プログラムを常駐→VxDでという指摘だろうけど
>>676
> bsfもbsrも知っていますが、残念ながらx86系ではないので・・・

CPU は ?
ビットサーチ命令はないの ?

> 演算でできれば美しいなぁと思いまして・・・

趣味なん ?
趣味なら別にいいけど、他人が保守するプログラムで凝ったことすると迷惑なだけだよ。
698デフォルトの名無しさん:04/01/25 23:06
>>697
そりゃ趣味ですよ
仕事のは、静的解析結果を一緒に提出しなきゃならんし
MISRA-Cとかは、符号付整数に対して論理演算もしちゃだめだから
まるで御伽噺のようだなw
>>694
> 呼び出し元がVBなんで・・・ ←処理遅そう
遅くないから呼び出し元でデータ保持して解決。
初心者の人ほど「○○だから遅いんじゃないか」とか気にするな。
迷ってる暇あったらベンチマークしてみろよ、とか処理系の心配する前に
その腐れアルゴリズムを何とかしろよ、とか色々思うんだがどうか。
と言うか、ベテランでも昔の知識そのままに「VB はインタプリタだから〜」とか言い出す奴がいたりする。

まあ、各種の言語や処理系が百花繚乱している現在、全部の言語に付き合うわけにはいかんから...

まず、実測してみる

これに尽きる。>> 自分も含めてな。
処理遅そう≠処理遅いってことに>>690は認識したんだろーか。
さっさと試せばいいのに。
速度の話題が出てたんで、ちょいと質問を。
for( ; ; )とwhile(1)、どっちが早いとかあります?
gccで比べるとどれだけ回しても有意な差が見られないんですが、うるさい偉い人がいるもので・・・。
うるさい偉い人馬鹿な人
同じものに最適化される筈。
gcc (GCC) 3.2 20020927 (prerelease)
で実際に比較してみたら、同じコードを吐いてた。
以上。
708704:04/01/26 04:53
深夜なのにみなさんありがとうございました。

ついでにうるさい偉い人に、波風立てずに穏便に
「あんたの言うことはいつも間違ってるよ」
という旨を伝える方法がありましたらご教授願いたく・・・(スレ違い?)
>>708
あなたの周りの無能な上司
http://pc.2ch.net/test/read.cgi/prog/1032970514/
>>704
使用しているコンパイラでのアセンブリ出力をその阿呆に提示しろ。
それでも御託を並べるようならその上に直接言え。
>>710
そいつが阿呆であることには同意だが、
アセンブリ出力のみを反論の根拠とする奴も
五十歩百歩だと思う。
>>704
その人はどっちを使えと言ってるの?
非常に単純に比較したら、forの方が1割くらい速かったよ
最適化してるか?
714(゚д゚)<シメジ:04/01/26 09:01
label:

goto label;
これが一番速いネ
>>714
gcc (GCC) 3.3.1 (cygming special)
で実際に比較してみたら、同じコードを吐いてた。
以上。
716デフォルトの名無しさん:04/01/26 09:24
>685
あんごうかしてもロックはかからんのだが?
>>704
数年前は、どっちだかが早いという情報が出回っていた
for(;;)だったかな

当時のコンパイラの仕様ということになるか
コンパイラも進化してるからね
だからそれくらいのコード、ベンチーマー(略

> 数年前は、どっちだかが早いという情報が出回っていた
for (;;) ですな。while (1) は毎回 1 を評価するからその分遅くなる云々。
オプティマイザ書いた奴はどんな阿呆だったのかと小一時間問い詰めたくなる。
定数なのにな。
720デフォルトの名無しさん:04/01/26 11:11
593 :デフォルトの名無しさん :04/01/23 20:20
LinuxでCを使用しているのですが、_msizeに変わる関数はありますか?
721ヽ(´ー`)ノ:04/01/26 11:25
>>593(>>720?)
linux + _msize で検索したらヒットしたんだが……?
人に聞く前に調べる癖付けような。動くかどうかは知らん。
http://www.umekkii.jp/data/program/c_lib/my_alloc/

malloc/calloc/realloc で確保したメモリ領域のサイズを後から得る方法は
(仕様の上では)存在しない。そもそも動的確保した時にサイズは分かってるん
だし、移植性を考える上でも size_t と一緒に持ち回った方がいいよ。
722デフォルトの名無しさん:04/01/26 12:05
質問です。これをメイン関数内で実行するとSignal11が出ます。
startがnullの時にうまくいかないみたいですが、
文法違ってるのでしょうか?

--------------------
メイン関数内
struct list *start = NULL;
add_list(start, 100);
---------------
struct list* add_list(struct list *start, int num)
{
if(start == NULL){
start = (struct list*)malloc(sizeof(struct list));
start->num_data = num;
start->nextlist = NULL;
}
else{
struct list *p = start;
struct list *newlist;

while(p->nextlist!=NULL){//スタート地点からリストの最後まで移動
p=p->nextlist;
}

p->nextlist = newlist;
newlist = (struct list*)malloc(sizeof(struct list));
newlist->num_data = num;
newlist->nextlist = NULL;
}
}
>p->nextlist = newlist;
>newlist = (struct list*)malloc(sizeof(struct list));
とりあえずここはおかしい。
724722:04/01/26 12:17
すみません。構造体の定義が抜けてました。

struct list {
int num_data;
struct list *nextlist;
};

>>723
確かに逆でした・・・
これを修正しましたが、
どうも第一回目の実行でSignal11が出るようです。
(start == NULL)の処理のどこかまずいのでしょうか?
struct list* add_list(struct list *start, int num)

なのに値を返してないぞ。
add_list 内の start に代入しても
main 内の start には代入されないぞ。
>>725
エラーか警告が出て気づきそうなものだけどな。
728デフォルトの名無しさん:04/01/26 12:31
小数点第2位を四捨五入するプログラムを作っているのですが、なかなかできません
#include(stdio.h)
main()
{
char c[10];
double a,b;
scanf("%lf",&a);
b=a+0.5;
sprintf(c,%c,b);
printf("%c%c%c",c[1],c[2],c[3]);
}
何か間違いがあるんでしょうか?
>>728
突っ込み所満載だが、とりあえず

 「そのソースのどこで『小数点第2位を四捨五入』しているつもりなのか?」

と問いたい。
730デフォルトの名無しさん:04/01/26 12:40

バイナリデータをテキストファイルに変換するプログラムって
どうつくったらいいですかね?ヒントだけでいいんで教えてください。
>>730
BASE64とかでエンコードすれば?
>>730
どういうバイナリデータをどういうテキストデータに変換したいんだ?
>>728
printf("%.1f\n", a);
734722:04/01/26 14:14
>>725-726 確かにそうでした。
return でstartのアドレスを戻し、
それをメイン関数でstartのアドレスに代入することで解決できました。
どうもありがとうございました。
--------------------
メイン関数内
struct list *start = NULL;
start = add_list(start, 100);
start = add_list(start, 200);
---------------
struct list* add_list(struct list *start, int num){
//numで示されるデータをリストの最後に追加
struct list *p = start;
struct list *newlist;
if(start == NULL){
start = (struct list*)malloc(sizeof(struct list));
start->num_data = num;
start->nextlist = NULL;
return start;
}
else{
struct list *p = start;
struct list *newlist;

while(p->nextlist!=NULL){//スタート地点からリストの最後まで移動
p=p->nextlist;
}
newlist = (struct list*)malloc(sizeof(struct list));
p->nextlist = newlist;
newlist->num_data = num;
newlist->nextlist = NULL;
}return start;}
たじゅぅ〜ん
736デフォルトの名無しさん:04/01/26 23:26
それ以外に俺は、
>else{
>struct list *p = start;
>struct list *newlist;

>while(p->nextlist!=NULL){//スタート地点からリストの最後まで移動
>p=p->nextlist;
>}
>newlist = (struct list*)malloc(sizeof(struct list));
>p->nextlist = newlist;

のpが気になるんだけど、Cでブロック内宣言のスタック変数て、
ブロック外になっても保持されるの?
737デフォルトの名無しさん:04/01/26 23:27
>>736
あ〜ごめん、先頭でも宣言してたんだね
ブロック内外に同じ変数名だとデバッグで死ぬからやめて欲しいなぁ。
classメンバはオールpublicな俺はC向き〜そして意味もなくfriend関数いっぱいの俺はアメリカン
なんで int と float を分けたんだろう。
1 も 1.0・・・ と考えれば float になると思うのに。
でも、きっとデニス先生は頭がいいから僕には分からない理由があるんだろうな。
処理の速さの問題かな。
741デフォルトの名無しさん:04/01/27 14:00
ふと疑問に思ったのですが、どうしてたかがプログラムを終了させるのに
ライブラリが必要なんでしょうか。
exit文として言語に組み込んであった方がいいのにと思うんですが。
742デフォルトの名無しさん:04/01/27 14:00
743デフォルトの名無しさん:04/01/27 14:04
どうして文字列をコピーするだけでも関数を呼ばないといけないんでしょうか。
>>743
必ずしもそうではない。いやなら自前のfor文でコピーしろ。
>>741
必ずしもそうではない。main関数内ならreturnで終了させられる。
746741:04/01/27 14:30
>>745
もちろんそれは知ってますよ。(^^;
exit は制御構造の1種だと思うんで、関数呼び出しというのは変な気がしませんか?
もしかしたらアーキテクチャ的に不可能なのかなとも思ったのですが。
美しい(だけの)制御構造にしたいんだったら
mainに戻ってからreturnするように書け
あと、setjmpとlongjmpの勉強しとけ
748びら:04/01/27 14:43
携帯から失礼します。
VB.netとCで作るDLL間で構造体の配列の受け渡しをしたいのですが上手くできません。
どうすれば実現出来るか知っている方いますか?
749デフォルトの名無しさん:04/01/27 14:47
関数の中のみで有効な#defineみたいなのは無いでしょうか?
const int size=256;
char str[size];
はc++ではできるのですが、cだとできないので。
750デフォルトの名無しさん:04/01/27 14:51
>>749
ありません。
関数の最後でundefすればいいんじゃないでしょうか。
ちなみにenum{size=256};char str[size];とやれば似たようなことはできます。
751749:04/01/27 15:28
>>750
分かりました。お答えいただきありがとうございました。
早速使わせていただきます。
752デフォルトの名無しさん:04/01/27 16:27
生まれた月と日を入力し、星座が何であるかを出力するプログラムを作りなさい。
ただし、誕生日を星座の関係は次のとおりである。

山羊座(12/23-1/20)
水瓶座(-2/18)
魚座(-3/20)
牡羊座(-4/20)
牡牛座(-5/21)
双子座(-6/21)
蟹座(-7/22)
獅子座(-8/23)
乙女座(-9/23)
天秤座(-10/23)
さそり座(-11/22)
いて座(-12/22)

実行結果
何月生まれですか?

何日生まれですか?
27(入力)
7月27日生まれのあなたは
獅子座です!!

※構造体をしようすること!!
 使用しているプログラムは削除します!
> ソース丸投げ、宿題、書籍 は専門の別スレがあるのでそこへさようなら。
>>752
>>752
宿題は自分でやってね。馬鹿。
755デフォルトの名無しさん:04/01/27 16:40
聞きたいことがあるんですけど。
>>755
スレ違い!あっちいけ!
757722:04/01/27 17:07
助言に基づいてこう変更しました。グローバルと変数が名前かぶるとまずいんですね。
おかげさまで完成したみたいです。ありがとうございました。
--------------------
メイン関数内
struct list *start = NULL;
start = add_list(start, 100);
start = add_list(start, 200);
---------------
struct list* add_list(struct list *st, int num){
//numで示されるデータをリストの最後に追加
struct list *p = st;
struct list *newlist;
if(start == NULL){
start = (struct list*)malloc(sizeof(struct list));
start->num_data = num;
start->nextlist = NULL;
return st;
}
else{
struct list *p = st;
struct list *newlist;

while(p->nextlist!=NULL){//スタート地点からリストの最後まで移動
p=p->nextlist;
}
newlist = (struct list*)malloc(sizeof(struct list));
p->nextlist = newlist;
newlist->num_data = num;
newlist->nextlist = NULL;
}return st;}
頭が混乱してきたよ〜へ ル プ みぃ
class Data{
public:
int a=0;
int b=0;
int c=0;
};
として、
class myclass{
Data fdata;
public:
myclass(Data &a){fdata=a;}//コンストラクタ
};

main(){
myclass *obj;
Data *data;
data=new Data;
obj=new myclass(data[0]);
}

としたとき、myclass objは、生成されたとき、メンバーfdata分も領域が確保されちゃうのでしょうか?
>>758
そりゃそうだ。
最適化に優れたコンパイラなら大丈夫だろうけど。
>>759 さっそくのレスありがとうございます。
うーやっぱりか〜 やだな・・・。
>>758
C++の質問はC++相談室で。
int kansu(){
int a;
return 0;
}
のように、関数内で定義したaは、returnされるとメモリー上からfreeになるのでしょうか?
>>762
なる。
厳密に言えば未使用スタックということになる。
>>763 サンクス
.未使用スタックとfree()で開放したものとの違いはなんですか?
ヒープメモリについて調べれ
if(ans==(1|2|3))printf("こんな簡略化した書き方がしたい");
if((ans==1)|(ans==2)|(ans==3))printf("これ書くのめんどくさい");

なんとかしてください
お願いしますm(__)m
#define (ans==(1|2|3)) ((ans==1)|(ans==2)|(ans==3))
>>766
どうでもいいが、その|は||の間違いか?
ビットごとにORをとる意味がわからん。
if (1 <= ans && ans <= 3)
770デフォルトの名無しさん:04/01/27 22:05
>>757
だから、
>else{
>struct list *p = st;
>struct list *newlist;
が嫌と言うちょろうが!
771デフォルトの名無しさん:04/01/27 22:06
switch (ans) {
case 1:case 2:case 3:
 ・・・
 break;
}
>>768
意味としては間違いだと思うが、結果的に正しく動くところが怖い。
773768:04/01/27 22:15
>>772
ワラタ
確かにそうだ。
0|0|0==0
0|1|0==1
1|1|0==1
だもんな。
774初心者です…。:04/01/27 22:46
本当に下のプログラム作成にお手上げです…。
「1+2+5+10+17…と足していき、
100万まで繰り返し、100万を超過した値を初期値化(?)し、
1+3+6+10+15…の数列の法則で引き算を行い、0以下になるまでを
表示するプログラム」

#include<stdio.h>

main()
{
int i, n, sum
i=1;n=1;sum=0;

while(sum<1000000)
{
sum=sum+n;
printf("分かりません…",i, sum);
n=(数列の一般項が入るはず…)


…ほとんどできてませんが、
どうか教えてください。
お願いします…。
見たことある問題だなぁ・・・
答えるつもりはないけど、問題文に(?)って……バカ?
>>774
最初の数列は奇数を順番に足していってるように見えるな。
数列のn番目の項をN(n)とすると、

N(n) = N(n - 1) + 2n - 1
N(1) = 1

ってところだろう。

その次の数列は、自然数を足していってるね。
M(n)とすると、

M(n) = M(n - 1) + n
M(1) = 1

だ。ってここまではわかってるのかな。
>>770
今気がつきました。
ソースの方もそうなってました。アホじゃん・・・
>>774は宿題スレで答えた記憶がある。
引き算の部分もちゃんと書いてあるとなると別人か?
>>752
>※構造体をしようすること!!
> 使用しているプログラムは削除します!

これ、矛盾してない?
781デフォルトの名無しさん:04/01/28 13:58
下のようなマップを表すファイルを読み込んで二次元配列に入れたいんですが、
1,1,1,1,1,1
1,0,1,0,0,1
1,1,0,1,1,1
1,0,0,0,0,1
1,1,1,1,1,1
配列に入れるとき、
fscanf("%d,%d,%d,%d,%d,%d",map[i][0],map[i][1],map[i][2],map[i][3],map[i][4],map[i][5]);
のようにしてやっているんですが、この方法だと横が長くなったとき、現実的でない・・・。
他に良い方法は無いでしょうか?
782デフォルトの名無しさん:04/01/28 14:07
>>781
strtol
何はともあれ for 使え。
784デフォルトの名無しさん:04/01/28 17:31
すみません、VBでいうTRIM関数って、C言語にはないんですか?
文字列の前後のスペースを削除するやつです。文字列中のスペースは削除しないやつです。
もし無いのだったら、どなたかつくて下さいお願いします。
積極系にgoto使おうぜ?
>>785
俺は最近、状態変数を導入するくらいならgotoだ!と思って、
積極的にgotoを使いたい気分なんだが、まだ一回も使ったことがない。
俺も。
機会がないだけだけど。
よ〜し、明日から、if文内でreturnしたりせずに、
戻り値をどっかの変数に入れて、関数の最後にgotoするぞ
goto するのはいいんだけど、ラベル書くのがめんどくさい
駄目、課題提出のソースコードに
バンバンgoto使って先生にほめられましょう
1 名前:ひろゆき@どうやら管理人 ★[] 投稿日:04/01/28 12:40

ハンマー投げ機能を搭載しました。
名前欄にmurofusianasanといれて書き込むと、
【25m】【40m】などに変換されますです。。。





























793【20m】:04/01/28 22:53
どりゃ!
794【80m】:04/01/28 22:54
うほ〜
795【ファウル】:04/01/28 22:57
どうや?!
796【17m】:04/01/28 22:58
>>794
おぬし…負けるかぃ!
797【40m】:04/01/28 23:02
>>796
残念!
798【180m】:04/01/28 23:05
室伏、根性見せたれ!
799【0m】:04/01/28 23:07
ん?
800muro o060189.ap.plala.or.jp:04/01/28 23:34
ハンマー
801muro o060189.ap.plala.or.jp:04/01/28 23:35
何だよみんな楽しそうにしやがって…_| ̄|○
802muro o060189.ap.plala.or.jp:04/01/28 23:36
てっきりネタじゃなくてホントかと思ったじゃないか…_| ̄|○
ヽ(`Д´)ノ
もうコネ━━━━(゚д゚;)━━━━ヨー
だからネ○トワ○クプログラミング相談室のやつらにネタスレとバカにされるんだよ。
805デフォルトの名無しさん:04/01/28 23:43
mallocを用いて任意の大きさの二次元配列を確保するための
具体的な記述を教えてください。
FAQ読みやがれ
>>800-803
     ●
  ddノ|)
_| ̄|○ <し





    ○
   .∵  ● ノ
   ':.  | ̄
_| ̄|  / >
不死アナさんに必ず引っかかるやつが出てくるんだが、
こんなことじゃ日本の未来が心配ですな...。
しかもここはプログラム板だぞ!
809muro o060189.ap.plala.or.jp:04/01/29 00:38
>>808
串通してわざと踏んだに決まってるだろ。
釣られんなよ。
>>809
あんたおもろいからそれをコテハンに汁!
811デフォルトの名無しさん:04/01/29 00:55
別ファイルで定義している構造体の配列を、externで宣言して利用しようとするとエラー
が出ます。

struct st {
int no;
char name[100];
}

struct st st1[2]={{1, "aaaa"},{2, "bbbb"}};

これをextern struct st st1[]とか宣言して、
st1[0].nameとかしたいんですけど。。。
構造体の定義のあとにセミコロンが無いのが気になる
>>811
メンバにアクセスしたり、構造体のサイズをとったり、
構造体の実体を定義したりするときは構造体のタグ名だけじゃなくて、
完全な構造体の定義が必要なんだけどその辺はどう?

タグ名だけ見せてコンパイルを通せるのはポインタのみだよ。
という問題じゃない?
>>811 エラーメッセージ貼れよ
815デフォルトの名無しさん:04/01/29 01:28
>>813
つまり、externを宣言する前に
struct st {
 int no;
 char name[100];
};
を書けってことですか?
816デフォルトの名無しさん:04/01/29 01:34
他のファイルでも構造体を使うなら、定義はヘッダーファイルに入れておけ。
だからエラーメッセージ教えれ
int m[100][100];
の2次元配列を用意して、0で初期化したいんですが、
memset(m,0,sizeof(int)*100*100);
でいいでしょうか?
また、forをつかって0で初期化するのとどっちが早いですか?
819デフォルトの名無しさん:04/01/29 12:29
>>818
0クリアならint m[100][100]={0};
静的変数(グローバル変数含む)ならそれすら必要ない。
>>819
!!!ちょいびっくり…。そんなんできたんだ・・・。いままでなにやってきたんだろ俺。
あーでもそれだとプログラムの途中で0セットできないんですね。
あくまで宣言の時か・・・。
プログラムの途中で0セットしたいときは、>>818で正しいですか?
>>821
途中で全ての要素に0をセットしなければならない様な設計に
問題がありそうな気がするのはオレだけか?
unsigned charの 0 をsizeof(int)個だけ並べたら、
intの0になるって保証あったかなぁ
>>822
お前だけ。
>>823
0 は流石に大丈夫だと思いたいんだけどなぁ。
>>823
ある
>>823
ある
0.0やNULLはだめだけど
>>823
そんな保証はないけど
それが問題になるシステムも現存しないでしょう。
>>823が言っているのはint n;memset(&n,0,sizeof(int));のことでしょ?
それなら保証されているはず。
連続したメモリの0クリアだから、memset()が最適だと思う
この場合、sizeof(m)で良い
0クリアするマクロにしておくと楽 (MemClear(m)みたく)
なお、sizeof(int[100][100]) という書き方も有る
>>830適切なアドバイス サンクスふぉーゆー
goto 1 ;
>>832
エラー
C言語初心者です。
どこかのホームページに「プロほどscanf関数は使用しない」と書いてあったのですが、なぜでしょう。
だれか、おすえて。
>>834
>>587
scanf に関する話題はさんざん既出です。
過去ログ読んでください。
>>834
それはscanfすらロクに使いこなせなかった適性の低すぎる素人さんのページです。
あんなちょろいので音を上げているようではどこへ行っても通用しません。
てきとーに生暖かく見守る気持ちでスルーしてあげて下さい。
グローバルで
struct {
float x;
float y;
float z;
float Angle;
} View;
を宣言しておいて、他のファイルで作ったプログラムでこの構造体を使いたい場合
どういう書き方で宣言すれば良いですか?
>>837
そのまま各なら

extern struct {
float x;
float y;
float z;
float Angle;
} View;

だと思うけど、その構造体に何か名前をつけたら?
>>838
ありがとうございます。
何個も宣言するわけじゃないからタグ名はいいかな?と・・・。
「タグ名なしは譲れない」ってわけじゃないのね。

複数のソースから参照する場合、
普通はヘッダでexternを付けて宣言し
ソースの1つでexternなしで実体を定義するから
構造体の定義と変数の宣言は分けた方が良いよ。
そうするためにはタグ名が必要。
もちろんtypedef名でも良いけどね。
842gets房:04/01/30 01:45
scanf関数の文字列入力で、最大サイズを動的に指定することはできますでしょうか?
sprintfか何かで書式文字列を設定したら?
844gets房:04/01/30 02:02
あ、その手がありましたね

どうもありがとうございます(^0^)/
複数の独立した配列について,コピーをしたい時になるべく早い方法を教えてください。
@
for(i=0;i<=50;i++)a1[i]=b1[i];
for(i=0;i<=50;i++)a2[i]=b2[i];
for(i=0;i<=50;i++)a3[i]=b3[i];

for(i=0;i<=50;i++)an[i]=bn[i];

A
for(i=0 ;i<=50;i++){
a1[i]=b1[i]
a2[i]=b2[i];
a3[i]=b3[i];
 |
an[i]=bn[i];
}

@Aどちらが処理が早いですか?変数(an,bn)は全て同じ型だとします。

当然A
>>845
ある程度配列が長くて
CPU がブロックコピー命令 (Intel 系の MOVSD とか) をサポートしていれば

(3)
memcpy(a1, b1, 50 * sizeof *a1);
memcpy(a2, b2, 50 * sizeof *a2);
 |
memcpy(an, bn, 50 * sizeof *an);

の方が速い。
>>846
それはキャッシュやオプティマイズを考慮した発言か?
考慮してない発言ですが、何か?
>>845
二次元配列は使えないのか ?

ホントにそこで時間がかかって困っているのか ?

最適化を議論する前にやることがあるような気がする。

(趣味とか興味ならまあいいけどね。)

>>849
(>>846 とは別人かも知れんが) だったら、断言なんかするな、ヴォケ。
>>845
それぞれのコードのプロファイルを取ればどちらが速いかすぐにわかる。
キャッシュと仮想記憶がからむので、nの数と実行環境によって変化する
一方が速いという結論が出ても、その環境だけでの話
テキストファイルから設定を読み込むようにしたいんですが、
何故か上手く動かないです。教えて頂けないでしょうか…。

#define MAX_SETTING 100
struct INI { char *label; char *value; } init[MAX_SETTING];

int loadsettings (void) {
  static char buff[2048];
  static char *buf;
  static char initfile[64];
  int i = 0; int j; FILE *ifp;
  
  sprintf(initfile,"./%s.txt",id);  // 設定ファイル名定義
  ifp = fopen(initfile,"r");
  if (ifp == NULL) { errors("Open Error initfile"); exit(0); }
  rewind(ifp);
  while (1) {
    if (fgets(buff, BUFF_SIZE, ifp) == NULL) { break; }
    buf = buff;
    init[i].label = buf; init[i].value = buf;  // とりあえず代入
    //printf("%d\t%s\t%s\n",i,init[i].label,init[i].value);
    i++;
  }
  fclose(ifp);
  for (j = 0; j < MAX_SETTING; j++) { printf("%d\t%s\t%s\n",j,init[j].label,init[j].value); }
  return 0;
}
>>853
まずどう動かないのよ?
なんでこう「うまくうごきません」とかしか言えない奴が多いのだ。
>>853
「id」はどこで定義してるの?
>>852
実際に使用するソースの候補を複数作成し、
その環境でプロファイルを複数回取り、
もっとも速いものを選択すればいいだけの話でしょ?
配列の先頭アドレスを代入するだけで
文字列のコピーが出来るわけがない
>>854
そんなことは実際にコンパイルすれば分かるじゃないですか。
860853:04/01/30 12:28
すみません。値が、ちゃんと代入されないんです。
printf("%d\t%s\t%s\n",i,init[i].label,init[i].value); で見ると上手く行くんですが、後ろの
for (j = 0; j < MAX_SETTING; j++) { printf("%d\t%s\t%s\n",j,init[j].label,init[j].value); }
部分では、設定ファイルの"一番最後の行"が init[0].の初めから終わりまでデタラメに代入されているんです。

init[0].label =>  "最後の行"
init[0].value => "最後の行"
init[1].label => "最後の行"
init[1].value => "最後の行"
init[2].label => "最後の行"
init[2].value => "最後の行" こんな感じです。

手で、代入したら上手く行くので while 文の中の代入なのでしょうが、
僕には原因が特定できないんです。
>>860
「%s」を「%p」に変えてみろ。
そして、その結果の意味をよく考えれ。
862バカでマ抜けな853:04/01/30 12:34
>>857
鋭い突っ込みありがとうございます。
なんでこんな事に気付かなかったのか不思議です…。
// きっと才能がないのですね…泣

>>856
idは、グローバル変数としてdefineの後に定義しています。
863バカでマ抜けな853:04/01/30 12:44
できました。こんな事で数日潰すなんて…。
我ながらCのセンスのなさに泣けてきます。

  while (1) {
    if (fgets(buff, BUFF_SIZE, ifp) == NULL) { break; }
    if (i >= MAX_SETTING) { break; }
    sprintf(init[i].label,"%s",buff);
    sprintf(init[i].value,"%s",strsplit(init[i].label,"="));
    i++;
  }
>>859
僕が、逆ギレしてる様な状況作らないで下さいよ。
>>861
そうでした。ありがとうございました。
>>863
おいおいホントにそれでいいのか ?
>>853 の方がましだと思うのは、俺だけか ?

ちなみに、
>     if (fgets(buff, BUFF_SIZE, ifp) == NULL) { break; }
>     if (i >= MAX_SETTING) { break; }
と言うのは、確かに「センス」が悪い。
>>863
( ゚д゚) ポカーン…
>>863
>struct INI { char *label; char *value; } init[MAX_SETTING];
おまいさ、ポインタ配列沢山とっても文字列格納する場所が無ければ仕方ないべさ。
典型的なC言語初心者だな。ポインタの勉強をしなおした方がいいぞ。
868845:04/01/30 13:46
いくつかのためになる情報をありがとうございました。
結局環境依存するわけですね。
単純な、コピ作業だから、機械語になるときはもっと最適になるんじゃないかと思ったわけです。
一見すると、Aが早いような気がしたんですけど、メモリの変数の分散状況などを考えると
そんなに単純ではない気がしたので質問しました。

(・3・)エェー
Cでは常に領域が確保されているかどうか考えてプログラミングしないといけませんYO!
>>845
そういう問題は、memcpy とか memmove とかを使うのが正解だと思う。
これらの標準の関数を使えば、その処理系が対象とする環境に対して
コンパイラが様々なテクニックを使って高速化してくれることが
期待できる(勿論、別の機械や将来の環境に対しても)。

それらを使っても遅いと感じるならばアセンブラを使うべき。

速度のために標準の関数の使用を諦めた時点で
処理系非依存というメリットを捨てているのだから、
わざわざ中途半端にCで書く意味はない。
文字列の中で全角文字と半角文字を区別させる方法というのはありますか?
>>871
もともと区別されてる。
何がしたいのかもっと具体的に書け。
失礼しました。
「今の時間は17:00」という文字列の中で半角の「17:00」の部分だけを抜き出したいのですが、
全角文字の部分が邪魔になっています。
数字以外を表示させないようにしたのですが、余計なものまでついてきます。
「今の時間は」という部分が変わらないのなら、
char *p="今の時間は17:00";
p+=10;
とすれば、pに「17:00」が入る。
全角の部分が時によって変化するなら、
p=strchr(p,":");
p-=2;
これでいいのでは?
p=strchr(p,':');
に修正で。。スマソ
>>873
"今の時間は17:00"という表示の形式だけでいいなら
表示のみ
int main(void){
char *buf={"今の時間は17:00"};
char *p=buf+10;
printf("%s",p);
return 0;
}

17:00部分を保存するなら
int main(void){
char *buf={"今の時間は17:00"};
char s[10];
sscanf(buf,"今の時間は%s",s); 
printf("%s",s);
return 0;
}

とか。
ホントにそれでいいのか? JISだったりUnicodeだったりした場合は?
てか、その辺明らかになってない質問はあんまり意味がないような。
char型変数から \nを取り除く関数ってありますか?
879デフォルトの名無しさん:04/01/30 18:56

以下のような2列のデータがあり,その中にFILLという
文字が混ざっていて,そのFILLを削除し,数字だけを出力する
プログラムを教えていただきたいのですが・・
どなたかよろしくお願い致します.
文字配列に格納して…という感じでしょうか?
0.00082025 4.20357
0.00135519 4.0125
0.001504      -1.3375
0.00157644 -0.955356
FILL FILL
0.00177638 2.10178
0.00234031 -4.39464
>>879
grep
>>879
たまたまあなたと同じようなことを
訊いてる人がいるみたいだから
こっちを参考にしては?偶然数値も同じようだし。
http://www2.realint.com/cgi-bin/tarticles.cgi?pointc+12342
#include <stdio.h>
#include <math.h>

void main(void)
{
char g[19][54];
int x,y,i,j;
for(i=0;i<=19;i++){
for(j=0;j<=54;j++){
g[i][j]=0;
y=10*sin(10*j*3.14159265358979323846/180);
x=10*cos(10*j*3.14159265358979323846/180);
if(y==10-i){
g[i][j]='*';
}
if(x==10-i){
g[i][j]='*';
}
}
}
for(i=0;i<=19;i++){
for(j=0;j<=54;j++){
printf("%c",g[i][j]);
}
printf("\n");
}
}
884:04/01/30 20:42
2次元配列を用いて作ったグラフにx軸とy軸を書きたいんですが、どうすればいいのですか?
こんなにがんばって円周率使ってるのに
変数ぜんぶintなのがすばらしい。
コマンドラインにグラフ表示させるってなんかすごいな・・
まず、char g[19][54];って宣言するんだったら要素は0〜18と0〜53だ。
x軸y軸をどうしても表示させたいのなら、'|'や'-'をgの軸に対応する要素に入れれば?
887883:04/01/30 22:52
for(i=0;i<=19;i++){
g[i][j]=0;
printf("| \n",g[i][0]);
}
for(j=0;j<=54;j++){
g[i][j]=0;
printf("-",g[10][j]);
}
を下に追加。

あれ?軸がグラフの下に乗ってしまいます…。超初心者ですみませぬ…。
円周率はintでok!
だって、教科書に約3て書いてありゅもふ(*^ー゚)b  
私の今のプロジェクトはunix環境でコンパイルしています。

コンパイラがhex作成完了したときにコンソールに吐き出すメッセージが
ターミナルがunicode未対応で文字化けします。

オ・・マ・ン コ

って文字化けで表示されるのでコンパイルの度に(*´д`*)ハァハァしちゃって困っています。
890デフォルトの名無しさん:04/01/31 00:13
>>888
およそ3だ
>>888
せめて22/7にしておいてくれ。
892デフォルトの名無しさん:04/01/31 00:54
すみません。教えてください。
サイズ不定の配列の先頭要素を構造体を引数にして関数を
作りたいんだど、その関数を呼ぶとプログラムが止まってしまいます。
何かよい手はありますでしょうか。
日本語ってむずかしい
意味がわかりません。
日本語って難しいね
日本語がおかしいし
その関数と実引数のソースがないと判断しようがないな
897892:04/01/31 01:30
例えばこんなの

struct aho{
 int a;
 int b;
}

BYTE hairetu[] = {1,2,3,4,5,6,7,8,9,10};
int main(int argc, **argv){

 func((struct aho *)&hairetu);

 return 0;
}
void func(struct aho *hairetu){


}
>>892
的を得てないかもしれないけど、

×func((struct aho *)&hairetu);
○func((struct aho *)&hairetu[0]);

というふうにしたらどうかね?
>>897
アホとしか言いようがない。
なんだその見るからに危なそうなキャストは。
いったい何がやりたいんだ?
ついでに&hairetuは配列の先頭要素のポインタのさらにアドレスを取っているわけだが
駄目だ、そんな発言じゃ到底リニアには追いつけない
もっと精進するんだ
意味が分らないキャストだね。

配列はリニアなメモリの並びだけど、
構造体はパディングが入るかも知れない。
処理の中身が分らないけど、危険じゃない?
903892:04/01/31 03:15
>>902
このような場合はvoid *を引数にして内部で
キャストして使うのがやっぱり王道でしょうか。
構造体のバディングは一応気をつけて作ってます。
普通は
struct aho型で、受け渡しでしょ。

問題は、BYTE型の配列が
>BYTE hairetu[] = {1,2,3,4,5,6,7,8,9,10};
構造体のメンバ変数とメモリ配置が一致するとは限らない事。
構造体のパディングはコンパイラや環境依存だと思うんだけど?
どう気を付けてるの?
905892:04/01/31 03:39
>>904
いや、実際にはデータはもっとあほみたいにでかいんです。
でも、そのデータの先頭だけはフォーマットが決まっていて
そこを見て処理したいのです。
動作環境は常に32bitCPUなのでintのデータとchar[4]なデータだけです。
詰め物が入り込む余地はありません。
うーん。なんか&hairetuがあやすぃ。あやすぃすぎるぞ。
>うーん。なんか&hairetuがあやすぃ。あやすぃすぎるぞ。
これは凡ミスじゃなかったのか?
配列は式の中では、ポインタ扱い。
つまり
&hairetu == BYTE **
気付いてないの?

あとさ、言ってる処理ならstruct aho型で受け取って
関数内で、BYTE型にキャストじゃないの?
逆でしょ。
907892:04/01/31 04:01
>>906
解決しました。
どうやら&hairetuがレジスタの中をさまよっていたみたいです。
こんな深夜まで付き合っていただきありがとうぞざいます。
>>905
hairetu を渡そうがstruct aho*を渡そうが効率には
何の違いもないわけだが?
>>906
> &hairetu == BYTE **
嘘言っちゃいかん。
&hairetu の型は BYTE (*)[10]
>動作環境は常に32bitCPUなのでintのデータとchar[4]なデータだけです。
>詰め物が入り込む余地はありません。
微妙に意味が分らない?
intのデータとchar[4]なデータしか使ってないなら意味が分るけど、
intのデータとchar[4]なデータにしかならないって意味じゃないよね?
>>909
VCさんにでも言われたの?
だれも型とは書いてないと思うけど…
>>911
じゃ何なんだ?
VCは使ったこともない。
>>911
ふーん、じゃあなんで、配列のアドレスを取ったら BYTE** になるという説明なの?
型のこといってんじゃないの?
>>912
Cの規格
"配列は式の中ではポインタになる"
でその"&(アドレス)"
ポインタのアドレスだって事。

コンパイラ以外で"BYTE (*)[10]型"なんて扱うなんては知らないな。
更に言うと、gccとVCしか使った事ないが、VCでしかそんな事は言わないんじゃない?
>>914
知らなかったんなら、素直に「知りませんでした」と言え。
>>914
とりあえずC FAQ読んで来い
VC以外で"BYTE (*)[10]型"なんてほざく奴は
”知りませんでした”。
で、VCは使った事ない?
ふーーん。
>>914
ふーん、じゃあ君は &1 って式を見たら、
int型のアドレス取ってるから int* だと思うわけ?
そっくりお返しするよ。

C FAQの6.3を読め。
配列は"式"の中ではポインターになる。
>>918

0x01 でも 0x00000001でも 1だが?
どっからint型って出てきたの?
>>919
6.12読め
6.13もな
923918:04/01/31 04:34
>>920
だって君、左辺値を持たないものにアドレス演算子を適用して、
そのポインタが生成されるっていってるじゃん。
1も左辺値もたないからそういうこと考えるのかな、なんて思ったのよ。

って、あ。配列って左辺値もってんだっけか。すまんすまん。
取り消すよ。
>>921
意味分ってる?
6.12が言ってる事は
>配列への(キャストのない)参照はポインターを産み出す
int arr[任意];
arr == int *
って意味だよ。
>>924
そうです。arrはたしかにint*だが、ここでいってるのは&arrのことだ。
こいつはintの配列へのポインタを生成する。
こいつはint (*)[任意]だ。これはポインタよ。
if( a[i] > 0 && a[i+1] > 0 && a[i+2] >0  ・・・ ){ }
と書くのと、
if(a[i] >0)if(a[i+1]>0)if( a[i+2] >0 ) ・・・・{ }

と書くのでは、どちらが早いですか?
6.13の説明だと
int (*ap)[N];
で(*ap)[N]は配列だよな。
”配列は式の中ではポインターになる”
(*ap)[N] は式の中では "ap **"
>>927
(*ap)[N]は配列じゃありませんよ。
ていうか定義の一部を取り出してどうしようっていうの?

そこで宣言してるのはapでしょ。
ap自体はポインタですよ。
>>928
C FAQ 6.13
>本当に配列そのものへのポインターが必要な場合は「int (*ap)[N];」 のような表現を使う。ここでNは
 ”配列”
のサイズを表す
>>929
でしょ。ポインタだよね。でそのポインタの指す物は配列なんですよ。
日本語分らないのか?
式の中での評価って無視ですか?
配列は”式”の中ではポインターになる

ポインタの配列は式の中では
"型 **"
>>930
もう相手しなくていいよ。
モウメンドクセ

6.12
> ANSI/ISO Cの元では&は「Tの配列へのポインター」を産み出す。

6.13
> 配列そのものへのポインターが必要な場合は「int (*ap)[N];」

んで、int arr[10]という定義があったと気はintの配列へのポインタだから、
その型はint (*)[N]だ。だから、

int arr[10];
int (*ap)[10] = &arr;

とできるのよ。apはポインタで、要素数10のintの配列を指す。
apはポインタであって配列ではないし、型はint**ではないよ。

疑うならapとap + 1のアドレスを見てみるといい。
本当にint**だとしたら、ap+1はポインタ分しか進まないはずだが、
実際は、sizeof(int) * 10だけ進むから。
ロクなプログラムも組めなさそうな奴らばっかだな。

ポインタを宣言して、其処にmallocで領域を確保する
ただし、関数に引数でポインタ変数を渡し、関数内でmallocする。

この場合を考えても分らないの?
>>933
頭悪すぎ。
apが"int *"
"*ap"はなんだ? intだろ。
>>935
違います
説明も出来ず
”違います”
か、おめでてーな。
938デフォルトの名無しさん:04/01/31 05:12
              \   ∩─ー、
                \/ ● 、_ `ヽ
                / \( ●  ● |つ
                |   X_入__ノ   ミ      釣られんよ。
                 、 (_/   ノ
                 \___ノ゙
                 / 丶' ⌒ヽ:::
                / ヽ    / /:::
               / /へ ヘ/ /:::
               / \ ヾミ  /|:::
              (__/| \___ノ/:::
大量につれたし、イキのいいの一匹いたし、そろそろ寝るか。
昨夜は盛況だったんだな.
配列の型はCの言語仕様がうまくいってない部分だから,誤解が
生じるのも仕方ない.

ANSI C 6.3.2.1
Except when it is the operand of the sizeof operator or the unary & operator, or is a
string literal used to initialize an array, an expression that has type ‘‘array of type’’ is
converted to an expression with type ‘‘pointer to type’’ that points to the initial element of
the array object and is not an lvalue.

原則として配列型の式はその先頭要素へのポインタに変換されるが,
&arrは例外だというのが嫌なところだ.そういう仕様にした意図は分かるが….
私にはどっちの解釈が正しいかは自信がある、だがどちらとは言わない
その代わりにこの配列とポインタに関する混乱を防ぐいい解釈の方法を示す

int i[10][5];
といった宣言を見つけたときは一番最後の配列の要素をintの隣に持ってくること
int[5] i[10]; /* int[5]型で10の要素をもつ配列i */
こういった解釈も可能だ。では次
int *p[10]; /* int*型の10の要素をもつ配列p */
この場合は[]は演算子の優先順位は最高なので移動することは出来ない。では次
int (*p)[10];
今度は[10]を左に持っていく解釈が可能である
int[10] *p; /* int[10]型へのポインタp */

このような記述は後発の言語Java C# Dなどで取り入れられている

さて、本題
int arr[10];
と宣言したときの arr は &arr[0] である
(むしろこの仕様が例外と考えるのが妥当と私は考える)

ところでarrの型は
int[10] arr;
と考えることが可能であるから
&arrの型は当然 int[10]へのポインタであり、C言語の記法で書くとすれば
int (*p)[10] となるのである

先に答えを言わないと宣言しておきながら言ってしまった自分に反省
942デフォルトの名無しさん:04/01/31 14:26
晒しあげてほしいのかな
>>935
>>int (*ap)[10];
>apが"int *"
apはint *ではない
演算子の優先順位は[ ]が最も上でその次に*が来る
[ ]の結合規則は左から右、*は右から左
なぜ*pに両端に( )がついているのかを良く考えること

int (*p)[10]; /* int[10]へのポインタp    */
int *p[10];  /* int*型の10の要素をもつ配列p */
両者は意味が異なる。
合わせて
int *foo();  /* int*を返す関数fooのプロトタイプ宣言 */
int (*foo)(); /* intを返す関数の関数ポインタfoo */
の意味の違いも覚えるように

これだけ詳細に解説しても分からないのなら今この違いを覚える必要は無い
#include <stdio.h>をおまじないとして覚えたように
この宣言もおまじないとして覚えるべきだ。いつか理解可能な日が来る
そのときまでは無理して理解する必要は無い。
現に多くのプログラマーは理解できていないのだから。
> 現に多くのプログラマーは理解できていないのだから。

いや、プログラマーなら普通は理解できてるだろ。
>>914,...,>>935がアホなだけ。
ん、、、理解できてない→理解できてる
この移行期間はかなり長いと思うが。
946デフォルトの名無しさん:04/01/31 15:14
>>919
> 配列は"式"の中ではポインターになる。
どんな式でもというわけじゃないYO!
&,sizeof,=の左辺(エラー),.の左側(エラー)等々。
理解できてると思ってるだけの人もいるYO>>900
こういうのがCのポインタの難しいところの1つだな。
アセンブラやれば済む問題でもないし。
949940:04/01/31 15:42
>>941
> int arr[10];
> と宣言したときの arr は &arr[0] である
> (むしろこの仕様が例外と考えるのが妥当と私は考える)

そうだな.
>>940では>>916の誤解に即して&arr : int[10]を例外と書いたが,
素直に言語を設計すればarr : int[10],&arr : int (*)[10]になるのが自然.
そして

・pが配列を指すポインタならばその要素参照は(*p)[i]
・pが配列要素を指すポインタならばその要素参照は*(p+i)

とし,配列のポインタ型への暗黙の変換は行わない.
これでみんな幸せになれる.
>>949
> >>940では>>916の誤解に即して&arr : int[10]を例外と書いたが,
失礼.int[10] → int (*)[10]の間違い.
配列とポインタを同一視する、ってのが無理があるんだよな
>>949
一番重要なarr[i]はどう扱う気だ?

しかし配列へのポインタって使ったことが無いな。
int ar[10];
int (**arps)[10] = malloc(sizeof(&ar) * 20);
arr[i]はarr[i]でいいと思うが…
>>953
配列がポインタに変換されるから、
arr[i] = *(&arr[0] + i)
でうまくいっているのだ、と言ってるんだが。

それとも、そもそもポインタpに対して
p[i] = *(p + i)
という変換はしない、ということか?不便だよ。
>>954
>>949
>・pが配列要素を指すポインタならばその要素参照は*(p+i)
と言っている。
無駄話うざい
>>955
>>954は、配列要素をさすポインタに限定した話ではない。

もしかして、
int *p = malloc(..);
のpはあなたの解釈では「配列要素をさす」ポインタになのか?
958956:04/01/31 15:58
もうすぐこのスレも終わりだからいいか。
>>954
そういうこと.
e[i]という式をeが配列型の時にしか使えないようにすれば,変な変換や
例外もなくなる.
まあCのやりたかったことも分かるけどね.
新スレ立ててこよう
どうやらみなさんポインタの使い方がわかってないようですね。
では、恥ずかしながら少しばかりですが、講釈でもしましょう。
char *p
これはchar 型を指すポインタのことです。
本来 char* pのほうが書き方がすっきりするし、実際1つだけなら
いいのですが、 char* p,q;などと書くとqはポインタではなくなるので注意
して下さい。
さて、ではどのように使うのかと言うと例えばchar a;などと宣言されて
いたとしましょう。
すると
p = &a; このようにpはaのアドレスを保持することができ
また *p = 'a'; などとすることにより、指している変数の値を自在に
変更できます。
これがポインタの基礎ですね。
まあ、Cはポインタはつまずきやすいところですので、あなたたちが
理解に苦しむのも仕方ないことだと思います。だけどそんなに
難しいものではないのですよ。
新スレです。
C言語なら俺俺に聞け! Part 72
http://pc2.2ch.net/test/read.cgi/tech/1075532838/
>本来 char* pのほうが書き方がすっきりするし、
解ってない証拠ですね。
>>961
そんなもん誰でも分かっとる。
問題はCの文法の煩わしさ。
レベルの差激しいな。
>>961はただの煽り(釣りとも言う)だろ
余談だけど、この手のスレって
話しが初心者中級者依存なのが
何かあれだよね
しょうがないけど
>>968
そーそーあんたは上級者 うん、えらい
>>968
はなしし、と書いてるので、日本語初心者。
俺は初心者ではないけど、いまだにポインタに関しては
時々コンパイラに怒られるな。
正直、ある程度C言語を使えるようになった人間は、
間違っても自分は言語をマスターしたとか、自信を持って上級者とはいえないと思う

いまだに文法でさえこんな書き方あったんだと思うことが時々あるし、
アルゴリズムや設計手法なんてどんどん新しいのが出てくるし(これは言語外かな?)、
脳内バグデータベースは毎日のように更新されるし・・・

※蛇足
最近文法で「へぇ〜」と思ったソースコード
http://pc2.2ch.net/test/read.cgi/tech/1042802490/200-201
>>972
>正直、ある程度C言語を使えるようになった人間は、
>間違っても自分は言語をマスターしたとか、自信を持って上級者とはいえないと思う

その一見謙虚そうな発言の裏には

神                 中級               初心者
|----------------------------|
    ^                                ^
自分のレベル                2chネラーの平均レベル

という>>972の脳内妄想が見え隠れしている気がしてならないが。
世間は広いぞ。
>>973
で、自分はその 脳内妄想も見通せるぞ というわけですか ?

あんたの思ってる世間が全てじゃないよ、たぶんね。
お前ら何言ってんだ?言語仕様をマスターするだけならそんなに大変なことじゃない。
自分のことを上級者だと思ってないやつが上級者のはずはない。
977972:04/02/01 20:05
>>973
はぁ、どうもです
ケチがケチをケチとけなすことは良くありますから

読む人にとっては私の文章はそう捕らえられてしまうと言うことが良く分かりました
>正直、ある程度C言語を使えるようになった人間は、
ここでの「人間」は脱初心者よりも上で上級者よりも下の人間(自分も含む)のこと
確かにこの文章だけを切り抜くと、初心者以上のすべての人間(自分は神寸前で見下ろす)
って意味になるよね

世間は本当に広かったです
実感しました
>>975の「上級者の定義」って?
聞いてみたいなあ、藁う目的で。
言語仕様をマスターしてるってことだろ (藁
K&Rってことだろ
>>979
初心者卒業でしかないやん
(・∀・)
>>970
>はなしし、と書いてるので、日本語初心者。
プ
いのしし
985985:04/02/02 19:19
最近、C言語を勉強しはじめました。
下記のようなサンプルプログラムを見つけたのですが、どのような処理を行うのでしょうか?
教えてください。
#define ABCD aaa, bbb, ccc, ddd, eee, fff, ggg, \
hhh, iii, jjj, kkk, lll, mmm, nnn,
と、記述するとプリプロセッサはどのように処理しますか?
単に改行が直前の\でキャンセルされてるだけだろ。
それとも、カンマ演算子がわからんのかね?
>985
どうしてその疑問を持った時に、
それをプリプロセッサにかける
という考えが湧かなかったのか
是非教えてくれないか?

そのうち、「パソコン本体の電源ボタンを押すと
どうなるのでしょうか。教えてください」なんて
聞いてくるんじゃないだろうな?
まあプリプロセッサの出力をチェック、なんて
そのうちいやでもやるかもしれんから覚えといたほうがいいなw
>>985
aaa, bbb, ccc, ddd, eee, fff, ggg, hhh, iii, jjj, kkk, lll, mmm, nnn,

へ置き換えられるようなマクロ ABCD が定義される。