- 1 名前:デフォルトの名無しさん mailto:sage [2009/10/06(火) 20:41:54 ]
- C言語の*入門者*向け解説スレッドです。
初心者、初級者の方は他の質問スレのほうが良いかもしれません。 教えて欲しいのではなく宿題を丸投げしたいだけなら ↓宿題スレ↓へ行ってください。 C/C++の宿題片付けます 130代目 pc12.2ch.net/test/read.cgi/tech/1250204272/ ・C++言語はスレ違いです。 ・分からない事をなるべく詳しく書いて下さい。 ・ソースコードを晒すと答えやすくなるかもしれません。 # 抜粋/整形厳禁、コンパイラに渡したソースをそのまま貼ること # サイズが大きい場合は宿題スレのアップローダ等を利用してください ・開発環境や動作環境も晒すと答えが早いかもしれません。 ・質問者は最初にその質問をした時のレス番号を名前欄に書いて下さい。 前スレ C言語なら俺に聞け(入門篇) Part 53 pc12.2ch.net/test/read.cgi/tech/1253110182/ 過去スレ makimo.to:8000/cgi-bin/search/search.cgi?q=%82b%8C%BE%8C%EA%82%C8%82%E7%89%B4%82%C9%95%B7%82%AF&andor=AND&sf=0&H=&view=table&D=tech&shw=5000
- 931 名前:デフォルトの名無しさん mailto:sage [2009/10/28(水) 02:04:04 ]
- どうしてそんなにsleepしたがるのだ。
OSに大麻イベントをセットしてWM_TIMERで読んでもらえばいいじゃないか。 え?ミリ秒単位で制御したいの? どっかのスレで誰かが副作用で暴れてたなぁ。
- 932 名前:デフォルトの名無しさん mailto:sage [2009/10/28(水) 02:13:11 ]
- >>927
#include <stdio.h> #include <time.h> #include <Windows.h> #include <conio.h> int main(void){ time_t timer; struct tm *t_st; while(1){ time(&timer); printf("現在時刻: %.24s\r", ctime(&timer)); Sleep(1000); while(kbhit()){ if(getch()==0x1b)break; } } }
- 933 名前:デフォルトの名無しさん mailto:sage [2009/10/28(水) 02:14:19 ]
- ごめん間違えた。
- 934 名前:927 mailto:sage [2009/10/28(水) 02:17:14 ]
- >>929
#define KEY_ESCAPE 0x1b int key; while()1{ key=getch(); if(key==KEY_ESCAPE) break; ・・・・・ } としてみたのですが、何かキーを押さないと時刻を更新しなくなります。 >>930 そうですよね。 強制終了ではなく、キー入力でwhileから抜けて処理終了を「きれい」と言っていました。 >>931 全く知識がないので、sleep使えば手っ取り早くできるかなと思いまして・・・・
- 935 名前:デフォルトの名無しさん mailto:sage [2009/10/28(水) 02:19:18 ]
- #include <stdio.h>
#include <time.h> #include <Windows.h> int main(void){ time_t timer; struct tm *t_st; while(1){ while(!_kbhit()){ time(&timer); printf("現在時刻: %.24s\r", ctime(&timer)); Sleep(1000); } if(_getch()==0x1b)break; } }
- 936 名前:デフォルトの名無しさん mailto:sage [2009/10/28(水) 02:23:55 ]
- エレガントじゃないな。
#include <stdio.h> #include <time.h> #include <Windows.h> #include <conio.h> int main(void){ time_t timer; struct tm *t_st; do{ while(!_kbhit()){ time(&timer); printf("現在時刻: %.24s\r", ctime(&timer)); Sleep(1000); } }while(_getch()!=0x1b); return 0; } こうだろ。
- 937 名前:927 mailto:sage [2009/10/28(水) 02:37:30 ]
- kbhit()なんてものがあったんですね。
もしお時間があれば、>>931さんの言うタイマーイベントを使ったプログラムのサンプルをお願いします。 私の環境はWinVista コンパイラ:Borland C++ 5.5.1 です。 よろしくお願いします。
- 938 名前:デフォルトの名無しさん mailto:sage [2009/10/28(水) 02:43:07 ]
- ボーランドのコンパイラなら
_kbhit() → kbhit() _getch() → getch() に置き換えだな。 MicroSoft は非標準には '_' を付けてる。
- 939 名前:デフォルトの名無しさん mailto:sage [2009/10/28(水) 02:44:59 ]
- Windows のタイマーイベントはウィンドウメッセージだから、
それを受け取るウィンドウが必要だぞ。
- 940 名前:デフォルトの名無しさん mailto:sage [2009/10/28(水) 02:48:35 ]
- つ select
- 941 名前:デフォルトの名無しさん mailto:sage [2009/10/28(水) 02:49:22 ]
- 宿題スレでもC++対応でそこに誘導している以上
このスレもC++拒否じゃなくて、無保証対応で 良くね?
- 942 名前:デフォルトの名無しさん mailto:sage [2009/10/28(水) 03:09:06 ]
- >>937
#include <stdio.h> #include <time.h> #include <Windows.h> VOID CALLBACK tp(HWND hwnd, UINT u, UINT_PTR p, DWORD dw){ time_t timer; struct tm *t_st; time(&timer); printf("現在時刻: %.24s\r", ctime(&timer)); } int main(void){ SetTimer(0,0,1000,tp); while(getch()!=0x1b); return 0; }
- 943 名前:デフォルトの名無しさん mailto:sage [2009/10/28(水) 04:53:52 ]
- >>924
その本には char (*b)[8]がポインタの配列であると書いてるの? そうなら子供の落書き帳にでもしちゃいなよ
- 944 名前:デフォルトの名無しさん mailto:sage [2009/10/28(水) 04:55:35 ]
- うあ?
途中から char *(b[8])の話になってる。すまんこ。
- 945 名前:デフォルトの名無しさん mailto:sage [2009/10/28(水) 08:04:04 ]
- select
- 946 名前:デフォルトの名無しさん [2009/10/28(水) 23:03:47 ]
- >>924
> () > [] アホ
- 947 名前:デフォルトの名無しさん mailto:sage [2009/10/28(水) 23:38:34 ]
- >>946
なんとなくカンテーレ
- 948 名前:921=919 mailto:sage [2009/10/29(木) 00:24:38 ]
- >922
なんか、違う人間が同じ問にレスしてわけわかになっていますな。 >ならなんで >char *(b[8]); 宣言子においては*と[]では[]の方が結びつきが強いので char *b[8]; と char *(b[8]); は同じ。 かえって混乱するかもしれないけど『関数の仮引数の宣言部では』 void func(char b[N][8]); void func(char b[][8]); void func(char (*b)[8]); は全て同等。 ついでに上のbと下のcは別物。下の宣言同士は全て同等 void g(char *c[N]); void g(char *c[]); void g(char **c); >924さんはもちろん理解していると思うけど、 >間接参照するときは、(*b)[i]のようにしないと いやそこは普通はb[0][i]になるよね。
- 949 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 00:56:38 ]
- >>908-909
ざっと見て2つほど明らかなバグがあるけど面倒なので詳細は説明しない。 ・2つ目のwhileの条件 ・k デバッガの使い方を覚えて1行ずつトレースしてみるのいいと思うよ。
- 950 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 02:19:12 ]
- >>948
> >間接参照するときは、(*b)[i]のようにしないと > いやそこは普通はb[0][i]になるよね。 ケースバイケースじゃないか?
- 951 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 11:05:30 ]
- C言語を学び始めたのですが文字列の扱いで詰まってしまいました。
ある文字列について、任意のn番目の文字からx文字だけ参照したいときにはどんな関数を使えばよいのでしょうか? strcpyやstrncpyでは先頭からしか見ることができないので困っています。 ////////////////////////////// char STR[] char Buf[] sprintf( Buf ,"123,456\0"); ////////////////////////////// このようなコードがあるときにSTRにBufの5文字目から7文字目まで(456)だけ コピーするにはどうすれば… 任意のトークンで区切れるstrtokも状況によっては使えそうなのですが 挙動が分からずNullエラーになってしまったりして安定しません…
- 952 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 11:10:07 ]
- >>951
sprintf(Buf, "123,456\0"+4);
- 953 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 11:12:24 ]
- char Buf[10];
char *str = "123,456\0"; int start = 5; int end = 7; sprintf(Buf, "%.*s", end - start + 1, str + start - 1);
- 954 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 11:24:15 ]
- 速やか過ぎる返信ありがとうございます。
>>952のも>>953のもどちらも実行結果は正しいのですが 肝心の何故こうなるのかが理解できてません。ダメジャンorz >>952の方のはsprintf関数の挙動を調べればなんとなく分かりそうなのですが(文字列操作に+4って何事?状態) >>953のお方のは正直何が起こっているのかさっぱりです。ポイン・・・タ・・・? とにかくとっかかりは掴めたのでもう少し調べてみようと思います。ありがとうございました
- 955 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 11:27:00 ]
- Buf+4 は &Buf[4] と同じ・・・ と言ってもわからないだろうか?
正直、ポインタの理解なしに文字列操作は厳しいと思う
- 956 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 11:32:45 ]
- >>955
>Buf+4 は &Buf[4] と同じ だということを今知ったレベルでした。 ポインタはなんとなーく概念的にはつかんでいるものの使いこなすには至らず逃げてばかりだったので… ネットワーク間でデータをやりとりしたいため文字列操作に手を出さざるを得なくなったのですが ポインタの基礎から把握していないと駄目っぽいですね…
- 957 名前:953 mailto:sage [2009/10/29(木) 11:37:57 ]
- こう書けば読めたりするだろうか。
char str[10]; strcpy(str, "123,456"); sprintf(Buf, "%.3s", str[5-1]); /* 5文字目の添え字は4 */
- 958 名前:951 mailto:sage [2009/10/29(木) 11:47:59 ]
- >>957
お恥ずかしながらフォーマット指定子で .[整数] ってなんだっけ…レベルです。 そして%sでstr[4]を指定すると何故5文字目以降が参照されるのかもしっかり把握していません。 後者は sprintf(Buf,"%s",str); は str[0]から\0にぶつかるまで参照していたということなのでしょうか。 とにかく、今やってみたおかげで>>957に類するコードを入力したら 何故かは知らないけどこうなる!というのが分かる状態になりました… がそんなんでは使いものになりませんよね
- 959 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 11:52:29 ]
- >>958
プログラムは向いていない。
- 960 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 11:53:18 ]
- そもそも"123,456\0"と言う風に'\0'を文字列リテラルに入れている時点で文字列操作を理解していないことが判るじゃないか。
- 961 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 12:02:16 ]
- 悔しいけども正論過ぎて泣いた。
本なりサイトなりで勉強し直すのが一番早そうですね。 丁寧に教えて下さった方、ありがとうございました。 \0を手動で入れていたのは、 ネットワークから送り込まれてくるデータがバッファに際限なく溜まっていってしまうため 区切りとして入れたのですがきっとそんなことになってしまう時点で何かがおかしいんですねわかります。
- 962 名前:953 mailto:sage [2009/10/29(木) 12:08:20 ]
- >>958
%[整数1].[整数2]s と書くと、最低でも[整数1]幅、最大でも[整数2]幅という指定になる 最低幅に足りない場合は先頭にスペースが埋められ、最大幅を超えた部分は切り捨てられる。 ネットワーク間でのデータやりとりだと、最大幅に足りない場合は後ろにスペースを埋めたいという ニーズもあるかと思う。 その場合は %-[整数1].[整数2]s とすればいい。 そのうち慣れるからがんばれ。
- 963 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 12:15:15 ]
- >>961
ネットワークから流れてくるものは文字列ではない。あれは只のバイト列だ。 と言う意識がないといつまでもカスみたいなコードしか書けないよ。 # 某SIerのプロパーがまさしくそれなんだが…… 神経質な人は、文字列で扱うときはcharでバイト列として扱うときは(unsigned charをtypedefした)BYTEにしているくらいだ。 # それはそれで、文字列系の標準関数を使うたびにキャストする必要があるので時としてあれだけど。
- 964 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 12:18:29 ]
- >>961
? バッファに際限なくたまるというのは確かにそうなってる時点でなんか変だと思う。 recv近辺のコードを上げてくれたらなんか分かるかも。
- 965 名前:951 mailto:sage [2009/10/29(木) 12:27:47 ]
- >>963
なるほど、覚えておくと見やすくなるだけでなく色々活用できるんですねえ… >>963 今まで平気で文字列として扱ってきたのですがバイトだったのですか! …それを知ったところで今すぐ何かが変わるわけじゃないのが不勉強なところですが 保存したレスをいつか発掘したら意味がちゃんと分かるようになってるといいなあ… >>964 相談したいのは山々なのですが ネットワーク周りはDXライブラリの関数を使用しているので ここだとスレ違いな気がするのです。
- 966 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 12:40:43 ]
- >>965
念の為に捕捉。 >963は、ナル文字で終端されていることがはっきりしている場合を文字列と言っている。 終端されていないものにはstrlen()やstrcpy()などの関数が使えないから、意識しておかないとね。 だからと言って、受信バッファより多めにメモリを確保して事前にクリアするなんてのは下策。 尚sprintf()の場合は、>962にあるようにサイズ制限ができるからバイト列に対しても使えなくはない。
- 967 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 12:46:22 ]
- >>966
> >>963は、ナル文字で終端されていることがはっきりしている場合を文字列と言っている。 別に>>963がどうとかじゃないよね。 Cにおける文字列の定義の話でしょ。
- 968 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 13:02:58 ]
- >>967
異論避け。それほど他意はない。
- 969 名前:デフォルトの名無しさん [2009/10/29(木) 14:38:26 ]
- 1から40までの数のなかで、3がつく数字とさんの倍数をすべて表示するプログラムを教えてください。
- 970 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 14:43:03 ]
- >>969
puts("3 6 9 12 13 15 18 21 23 24 27 30 31 32 33 34 35 36 37 38 39");
- 971 名前:デフォルトの名無しさん [2009/10/29(木) 14:44:44 ]
- >>969
#include <stdio.h> #include <string.h> int main(void) { int i; char buf[32]; for(i = 1; i <= 40; i++) { sprintf(buf, "%d", i); if (i % 3 == 0 || strchr(buf, '3') != NULL) { printf("%d\n", i); } } return 0; }
- 972 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 15:59:09 ]
- #define _XOPEN_SOURCE
#include <stdio.h> #include <unistd.h> int main() { char a[100]; *a = crypt("hogehoge", "EV"); printf("%s", a); return 0; } crypt関数について調べようと思ってこんなん作ったんだけどaに何も入らないのはなぜ? crypt関数自体がアレなのかなと思って int main() { char a[100]; printf("%s", crypt("hogehoge", "EV")); return 0; } を試しに実行してみたけどこれはまともに動いた。
- 973 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 16:12:20 ]
- gcc -Wall
- 974 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 16:19:50 ]
- >>972
char a[100]; の時、a は &a[0] と同じ つまり、*a はa[0]と同じ a[0] = crypt・・・ が変なのはわかるだろ。 strcpy使え。
- 975 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 16:22:14 ]
- *a = crypt("hogehoge", "EV");
は a[0] = (char)crypt("hogehoge", "EV"); と同じ
- 976 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 16:49:46 ]
- C言語学びはじめてもうすぐ半年になるが、いつになったらタッチタイピングできるようになるんだ
- 977 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 16:57:47 ]
- >>976
英語配列に変えてみた、、がまだ慣れない。
- 978 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 17:53:51 ]
- >>976
プログラミングとタッチタイピングを同時に学ぼうと言うのがそもそも間違い。 プログラミングは、基本的にキー入力速度が速い必要はないからね。
- 979 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 18:11:08 ]
- どうせなら C でタイピング練習ゲーム作ったらどうか。
- 980 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 20:11:55 ]
- ビット演算について質問です
char aの上位4バイトに 64以下の整数char bを代入したい場合、 (a & 0b00001111) + (b << 4) でできるのはわかるのですが、 もっと単純な表記方法はあるでしょうか?
- 981 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 20:14:17 ]
- ゲームセンターにあるタイピングオブザデッドに憧れてタイピング練習しはじめて
ローマ字覚える前にタッチタイピングマスターしちまったなぁ 最近出た第二弾はわからんがタイピング覚える気ならゾンビ打マジおすすめ 本当の意味でゲーム感覚で覚えられるタイピングソフト 他にもいろいろタイピングソフトやってみたがまともなのはこれしかなかった スレチごめんね
- 982 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 20:17:20 ]
- 環境によっては
union {struct {unsigned ah:4; unsigned al:4} s; char c} a; として a.s.ah = b; と書ける。 或いは、 a = (a % 16) + (b * 16); とも書ける。 いずれの場合も、bが16以上の場合は破綻する。
- 983 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 20:18:43 ]
- >>980
>char aの上位4バイトに 64以下の整数char bを代入したい場合、 char aの上位4ビットに 15以下の整数char bを代入したい場合、 の書き間違いかな?
- 984 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 20:19:17 ]
- >>980
charの上位4バイトってなんだよpgr
- 985 名前:980 mailto:sage [2009/10/29(木) 20:19:56 ]
- >982
どうも 4ビットって64じゃなくて16でしたね… こんなんでビット演算とかやらない方が安全か
- 986 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 21:11:02 BE:284013465-DIA(352353)]
- 次スレ立てました
C言語なら俺に聞け(入門篇) Part 55 pc12.2ch.net/test/read.cgi/tech/1256818218/
- 987 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 22:10:01 ]
- >>985
「こんなんで・・・」はないと思うぞ。 1ビットでも必要な時はビット演算をする。 そもそも何のためにやるのかだよね。
- 988 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 23:37:27 ]
- >>957
プ
- 989 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 23:47:58 ]
- 屁こくな
- 990 名前:デフォルトの名無しさん mailto:sage [2009/10/29(木) 23:52:11 ]
- 間違いの指摘するならちゃんと教えてやれよ。
まあ、うっかりミスだろうから指摘するまでもないが。
- 991 名前:デフォルトの名無しさん mailto:sage [2009/10/30(金) 00:56:33 ]
- >>982
そのunionの使い方って厳密には保証されないんじゃないっけ?
- 992 名前:デフォルトの名無しさん mailto:sage [2009/10/30(金) 00:58:54 ]
- 俺にはその間違い探し難しすぎるぜ
- 993 名前:デフォルトの名無しさん mailto:sage [2009/10/30(金) 08:44:31 ]
- >>991
上下どちらのビットから割り付けるかは処理系定義なので 移植性はないけどもどっちかに決まっているはず。
- 994 名前:デフォルトの名無しさん mailto:sage [2009/10/30(金) 09:46:08 ]
- ume
- 995 名前:デフォルトの名無しさん mailto:sage [2009/10/30(金) 09:50:06 ]
- >>991
処理系によっては、妙な割り付け方をするかもしれないね。
- 996 名前:デフォルトの名無しさん mailto:sage [2009/10/30(金) 10:02:19 ]
- ume
- 997 名前:デフォルトの名無しさん [2009/10/30(金) 10:04:35 ]
- age
- 998 名前:デフォルトの名無しさん mailto:sage [2009/10/30(金) 10:18:54 ]
- >>992
>957のことなら、& str[5 - 1]だ。
- 999 名前:デフォルトの名無しさん mailto:sage [2009/10/30(金) 10:18:59 ]
- ume
- 1000 名前:デフォルトの名無しさん [2009/10/30(金) 10:21:41 ]
- 03e8
- 1001 名前:1001 [Over 1000 Thread]
- このスレッドは1000を超えました。
もう書けないので、新しいスレッドを立ててくださいです。。。
|

|