トップページ⇒tech
1001コメント370KB

C/C++の宿題を片づけます 49代目

■ このスレッドは過去ログ倉庫に格納されています
0001デフォルトの名無しさん2005/08/10(水) 17:10:47

あなたが解けないC/C++の宿題を片づけます
――【注意点】―――――――――――――――――――――――――
・質問は必ず【質問テンプレ】に従ってください。
・問題文は、解いてもらう方にわかりやすいように全文を書きましょう。
・計算問題は必ず数式をあげ、どのような計算をするのか詳しく説明してください。
・エラーは、その詳細と発生した行を書きましょう。エラーメッセージはコピペしてください。
・後から問題に付け足しするのはやめましょう。解いてもらっている方に失礼です。
―――――――――――――――――――――――――――――――

【質問テンプレ】
[1] 授業単元:
[2] 問題文(含コード&リンク):
[3] 環境
 [3.1] OS: Windows/Linux/等々
 [3.2] コンパイラ名とバージョン: gcc 2.9 VC 6.0等
 [3.3] 言語: C/C++/どちらでも可 のいずれか
[4] 期限: [yyyy年mm月dd日hh:mmまで] または [無期限] のいずれか (「できるだけ早く」は不可)
[5] その他の制限: どこまで習っているか、標準ライブラリは使ってはいけない等々

【アップローダー==ラウンジ】(質問が長い時はココ使うと便利 回答者もコードが長ければここに)
http://kansai2channeler.hp.infoseek.co.jp/cgi-bin/joyful/joyful.htm

【前スレ】
48代目: http://pc8.2ch.net/test/read.cgi/tech/1121471445/

【歴代スレは>>2-13】
0175デフォルトの名無しさん2005/08/22(月) 02:03:59
一番簡単なPascalインタープリタでも作れば?
p-code吐くソースならどこにでも転がってる希ガス。
0176デフォルトの名無しさん2005/08/22(月) 02:17:35
オリジナルでいいなら、Lisp風が一番簡単なんじゃない。
0177デフォルトの名無しさん2005/08/22(月) 13:48:34
0から100まで乱数で発生したデータファイルがあって、そのデータを整理したいです。

元のデータ
30
9
88
78
89
13
90
54
10

整理されたもの

0〜9     1個
10〜19   2個
20〜29   0個
   :
   :


お願いします
0178デフォルトの名無しさん2005/08/22(月) 14:08:28
>>177
エクスプローラーでファイル名順に並べ替えてやれば、
0、100、一ケタ台を除けば全部固まってるだろ。
それを矩形でまとめて選択してフォルダに放り込む。

もしかしてプログラムで整理?
0179デフォルトの名無しさん2005/08/22(月) 14:10:19
データファイル内にデータが入ってるんでない?
0180デフォルトの名無しさん2005/08/22(月) 14:11:31
>>177
とりあえず書いた
テンプレに従ってないので勝手にGCC(ANSI C)だってことにした
ファイルにそういうデータが書いてあるのを読み込んで処理すりゃいいんだよな?

#include <stdio.h>

int main(void)
{
FILE *fp;
unsigned int count[10] = {0};/*個数*/
int temp;

if ((fp = fopen("infile", "r")) == NULL) exit(1);
while (fscanf(fp, "%d", &temp) == 1) {
count[(int)temp/10]++;
}

for (temp = 0; temp < 10; temp++)
printf("%d~%d\t%2d個\n", temp * 10, temp * 10 + 9, count[temp]);

return 0;
}
0181デフォルトの名無しさん2005/08/22(月) 14:18:34
//0から99まででいいのかな?
#define FILENAME "file.txt"

#include <stdio.h>

int main()
{
 int ans[10]={0};
 char buf[3];

 FILE *fp=fopen( FILENAME ,"r");
 if(!fp) {return -1;}

 while(fgets(buf,sizeof(buf),fp))
  {ans[atoi(buf)/10]++;}

 for(i=0;i<10;i++)
  {printf("%d〜%d \t%d個\n",i,i+9,ans[i]);}                 

 fclose(fp);
}
01821812005/08/22(月) 14:19:44
かぶったゴメン・・・
0183デフォルトの名無しさん2005/08/22(月) 14:30:43
つ qsort()
0184デフォルトの名無しさん2005/08/22(月) 14:32:09
>>180
0から100だから、101通りあるよ。
>count[(int)temp/10]++;
0〜9の配列で10にアクセスしてしまう。

>unsigned int count[10] = {0};/*個数*/
これだと配列の最初だけしか初期化されないでしょ。
配列11個とって
{0,0,0,0,0,0,0,0,0,0,0};
またはSIZEOF(count)領域を初期化

>>181
> char buf[3];
これも2桁前提か。
データファイルが壊れてたらバグるな。
出力時ならいいけど、入力時はfgetsの最大値までちゃんととらんと。

> if(!fp) {return -1;}
>  {printf("%d〜%d \t%d個\n",i,i+9,ans[i]);}                 
中括弧は外したほうがまし

または
 if(!fp) {
return -1;
}
と表記して行の追加、削除をしやすくしたほうがいい。
行丸ごとコメントアウトしたり追加、削除したときに中括弧の対応が変わる。
0185デフォルトの名無しさん2005/08/22(月) 14:33:00
>>183
意味ないよ
01861802005/08/22(月) 14:41:36
>>184
手元のK&Rには初期化子が少ない場合には0で埋められるって書いてあるが
まぁどっちにしろ100の存在忘れてた・・・
0187デフォルトの名無しさん2005/08/22(月) 14:46:11
>>184
>これだと配列の最初だけしか初期化されないでしょ。
が意味わかんないし、
>>181は1行目に0〜99って書いてんだろ。。
しかもここは中括弧とかのお話するところじゃないのよボーヤ
0188デフォルトの名無しさん2005/08/22(月) 14:53:06
この場合sizeof(count)ってsizeof(int)と同じじゃない?
sizeofで配列のサイズなんか取れたっけ?
01891802005/08/22(月) 14:57:05
>>188
sizeof(配列名)の場合は配列全体のサイズじゃなかったっけ?
sizeof(配列名)/sizeof(配列名[0])で個数求めるとか、何処かで見た希ガス
0190デフォルトの名無しさん2005/08/22(月) 15:05:42
>>186
>初期化子が少ない場合には0で埋められる
知らなかったけど、これは目的の0とデフォルトの0が一致してるから省略可能
になってるっていうことを誤解しやすいよ。
配列がたくさんあると全部書くのは大変だけど。

static とかグローバル変数の宣言によっては初期化されないとかなかった?
全然覚えてないけど、コンパイラのバグとかもあったと思うし。
ヘッダで複数のファイルにインクルードするときに条件があったような。
サイズの違うバッファのコピーとか移動とかでゴミが残ったりとかもあるし

>>187
バグはオマエの脳内だけにしてくれよ。

出題で0〜100って書いてあるだろ。
それを勝手に〜99に変更してるだろ。
「やっぱり〜100だよ」と言われたら3箇所の修正が必要になる。
>unsigned int count[10] = {0};/*個数*/
> char buf[3];
> for(i=0;i<10;i++)

> char buf[3];
の修正を忘れたら壊れるだろ?
fgetsはバッファのサイズなんかチェックしてくれないぞ。

>>188
マクロのSIZEOFなんだけど、配列だろうとアロケートメモリだろうと
適切なサイズを取ってくれる。
初期化やコピー、サイズ比較するとき便利だし、サイズ変更時の修正もいらない。

sizeof(int)では、変数の型が変更されたら食い違うので使わない。
せいぜいsizeofの動作やintのサイズを確認するときくらい
01911882005/08/22(月) 15:06:48
ああ、スマン。調べてみたら出来るっぽいね。なんか勘違いしてたっぽい
0192デフォルトの名無しさん2005/08/22(月) 15:10:11
>fgetsはバッファのサイズなんかチェックしてくれないぞ。
>fgetsはバッファのサイズなんかチェックしてくれないぞ。
>fgetsはバッファのサイズなんかチェックしてくれないぞ。
>fgetsはバッファのサイズなんかチェックしてくれないぞ。
>fgetsはバッファのサイズなんかチェックしてくれないぞ。
0193デフォルトの名無しさん2005/08/22(月) 15:10:59
>>190
バグはオマエの脳内だけにしてくれよ。
0194デフォルトの名無しさん2005/08/22(月) 15:12:03
夏廚多すぎ
あんびりばぼーなスレになってるw
01951812005/08/22(月) 15:17:48
>>190
なんかスレが汚れてきててすごくいやなんだが、
とりあえず自分の見解を(多分また荒れるから今日はもう来ないぞw)

もし0〜100なんだったら
>0〜9     1個
>10〜19   2個
>20〜29   0個
>   :
>   :
という仕様の設定があいまいになるよな。100はドコに入るんだって。
あなた様は100は特別だ、ということでans[11]にしたいようだが、
そんなことは喪前の脳内で決まったことであってそれこそ書いてないぞ。
あと知ったかブリはやめとけyo
0196デフォルトの名無しさん2005/08/22(月) 15:18:08
いつもニヤニヤしながら見てるよw
0197デフォルトの名無しさん2005/08/22(月) 15:19:12
>>192
sizeof(buf) でサイズ指定してあったな。
確か割り当ては3バイトだな。
1、0、0、・・・NULLは入らないから、ま、いっか。

>関数は、入力文字列の読み込み時に、数値の一部として認識できない文字が現れた時点で停止します。
>この文字は、文字列の終わりを示す NULL ('\0' または L'\0') の場合もあります。

ふんふん。100として認識だな。どこを終端と認識してるんだろ。
bufの外には文字入れてないから問題ないだろうな。

さて次の文字だ。
¥r¥n
ん?改行コードを読み込めなかったか。
これは、0だな。
0〜9としてカウントすれば問題なし。


てことですか?
0198デフォルトの名無しさん2005/08/22(月) 15:19:46
>>177
テンプレ書いてないんで勝手にC++ってことにした。
#include <algorithm>
#include <fstream>
#include <iostream>
#include <iterator>
#include <vector>
int main()
{
    std::ifstream ifs("data.txt");
    std::vector<int> v;
    std::copy(std::istream_iterator<int>(ifs), std::istream_iterator<int>(), std::back_inserter(v));
    std::sort(v.begin(), v.end());
    for (int i = 0; i < 100; i += 10) std::cout << i << "〜" << i + 9 << '\t' << (std::upper_bound(v.begin(), v.end(), i + 9) - std::lower_bound(v.begin(), v.end(), i)) << "個" << std::endl;
    std::cout << 100 << '\t' << (std::upper_bound(v.begin(), v.end(), 100) - std::lower_bound(v.begin(), v.end(), 100)) << "個" << std::endl;
}
0199デフォルトの名無しさん2005/08/22(月) 15:24:59
>>197
下のほうに書いてあることはよくわからんが・・・
上のほうに書いてあるのはおかしいぞ?
参考:http://www.bohyoh.com/CandCPP/C/Library/fgets.html
0200デフォルトの名無しさん2005/08/22(月) 15:30:04
>>195
>そんなことは喪前の脳内で決まったことであってそれこそ書いてないぞ。
書いてないことを都合のいいように定義するのは問題ない。

>>198 も 
>テンプレ書いてないんで勝手にC++ってことにした。
って書いてる。

でも、はっきり書いてあることを勝手に変えた場合、
それが及ぼす影響はすべて変えたやつにある。
責任とれよってことだ。

>>199
文字列はNULLで終わる。
だから文字を読み取った後にNULLを追加してくれる。
しかし、バッファの最大値まで文字で埋まった場合はNULLを入れる場所がない。

だからMSのIEもアドレスが長すぎるとバグってた。
0201デフォルトの名無しさん2005/08/22(月) 15:31:12
>それが及ぼす影響はすべて変えたやつにある。

それが及ぼす影響はすべて変えたやつに 責任が ある。
0202デフォルトの名無しさん2005/08/22(月) 15:34:49
>しかし、バッファの最大値まで文字で埋まった場合
0203デフォルトの名無しさん2005/08/22(月) 15:35:09
1 + 1/r^2 + 1/r^2 +・・・・+1/r^n
rとnを聞いて
と求めるプログラム
を頼みます
0204デフォルトの名無しさん2005/08/22(月) 15:37:44
>>202
はいはい。
ごめんなさいね。
バッファの最後までって書けばよかったね。

>>203
計算誤差はどう計算しますか?
ちなみに漏れは作れません。
0205デフォルトの名無しさん2005/08/22(月) 15:38:58
>バッファの最後までって書けばよかったね。
・・・orz
0206デフォルトの名無しさん2005/08/22(月) 15:39:38
>計算誤差はどう計算しますか?
>計算誤差はどう計算しますか?
>計算誤差はどう計算しますか?
>計算誤差はどう計算しますか?
>計算誤差はどう計算しますか?
>計算誤差はどう計算しますか?
0207デフォルトの名無しさん2005/08/22(月) 15:42:27
>>203
1 + 1/r + 1/r^2 + … 1/r^n じゃないの?
0208デフォルトの名無しさん2005/08/22(月) 15:42:31
桁あふれる?それがわかんないと。。
ってかマルチじゃねぇ?
0209デフォルトの名無しさん2005/08/22(月) 15:42:35
>>206
nが大きいとあふれるし、少数以下の桁数が少ないと誤差が大きくなるから
そこを考えて計算しないといけないでしょ?
0210デフォルトの名無しさん2005/08/22(月) 15:43:23
>>209
計算誤差を計算してもその計算において計算誤差が出ます
02112092005/08/22(月) 15:46:57
あ、プログラム作ってからその問題を解決していきましょうってことかな?

>>210
だから、誤差を小さくするよう努力するとか、
プログラムがどこまで正常動作するかを計算してそれを仕様とするとか、
そういうことなんじゃないかと思ったんですが。

カレンダーにしたって何年から何年まで正しく動作するとかあるでしょ。
0212デフォルトの名無しさん 2005/08/22(月) 15:49:02
誤差は適当でいいだす
数字あふれてもかまいません
0213デフォルトの名無しさん2005/08/22(月) 15:50:13
>>203
とりあえず3項目はtypoということで。ついでにCで。俺(==>>198)節操ないなぁw
#include <stdio.h>
int main(void) {
    int n, r;
    double t = 1, a = 1;
    printf("n?:"); scanf("%d", &n);
    printf("r?:"); scanf("%d", &r);
    while (n--) a += t /= r;
    printf("%f", a);
    return 0;
}
0214デフォルトの名無しさん 2005/08/22(月) 15:52:44
cで書いてくれるのが
ベストです(・ω・)
0215デフォルトの名無しさん2005/08/22(月) 15:58:57
>>214
だからCで書いてんじゃん
0216デフォルトの名無しさん2005/08/22(月) 16:02:33
>>203
日本語がおかしいな。大丈夫か?

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

int main(void)
{
int n;
int r;
double result = 0;

printf("input n?:"); scanf("%d", &n);
printf("input r?:"); scanf("%d", &r);
int e;
for(e=0; e<n; e++)
{
result += 1 / pow(r, e);
}
printf("n=%d, r=%d, result=%lf\n", n, r, result);

return 0;
}
0217デフォルトの名無しさん2005/08/22(月) 16:06:52
>>216
>>203は1/r^nまで足してるからfor(e=0; e<=n; e++)じゃないかな
02182162005/08/22(月) 16:16:17
>>217
そうだった・・・指摘ありがトン

あと、>>203へ
>>216の結果は 1/r も含まれてるので、
入れたくなかったら自分で考えてループ調整してくれ。
0219デフォルトの名無しさん2005/08/22(月) 16:20:18
218さんありがとう

1 + x/1! + x^2/2! + x^3/3! +・・・・+x^r/r!
をとくプログラム
xとrをきくかたち
教えてください(>Д<)

0220デフォルトの名無しさん2005/08/22(月) 16:34:26
// x をきくかたち
printf( "? x = " );
scanf( "%d", &x );

// r をきくかたち
printf( "? r = " );
scanf( "%d", &r );
02211772005/08/22(月) 16:36:58
皆さん素早い解答ありがとうございます。
書いていただいたことを参考にしてやってみます。
02222162005/08/22(月) 16:47:23
>>219
計算結果が合ってるかどうかは自分で確かめて。

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

static long factorial(int n)
{
long result = 1;
while(n > 0){ result *= n--; }
return result;
}

int main(void)
{
int x = 2;
int r = 2;
double result = 0;

printf("input x?:"); scanf("%d", &x);
printf("input r?:"); scanf("%d", &r);
int n;
for(n=0; n<=r; n++)
{
result += pow(x, n) / factorial(n);
}
printf("x=%d, r=%d, result=%lf\n", x, r, result);

return 0;
}
02232132005/08/22(月) 16:50:56
>>219
#include <stdio.h>
int main(void) {
    int r, n = 0;
    double x, t = 1, a = 1;
    printf("x?:"); scanf("%lf", &x);
    printf("r?:"); scanf("%d", &r);
    while (n++ < r) a += t *= x / n;
    printf("%f", a);
    return 0;
}
02242162005/08/22(月) 16:57:54
ちなみに、
>>216を簡単にすると>>213になる。
>>222 → >>223も同様。

どちらも結果は同じハズ
02252132005/08/22(月) 17:05:59
>>203の3項目じゃなくて2項目だった
02262192005/08/22(月) 17:17:24
皆さんありがとう!!!!
02272162005/08/22(月) 17:48:43
ほんと今更だが、
質問する香具師はちゃんとテンプレ書けよな。
0228ぼるじょあ ◆yBEncckFOU 2005/08/22(月) 20:23:14
(・3・)エェー 俺も日本語ならわかるYO!
02291652005/08/23(火) 19:41:24
>>164
お陰様でstd::mapなんて便利なものがあることを知り、
平仮名文章→ローマ字プログラム作れました。ありがとう。
0230デフォルトの名無しさん2005/08/23(火) 22:18:51
lisp組んでます。
・・・とりあえず、空白とコメントを読み飛ばす処理を書きました。
次はトークン一つ取ってくるところです。
でも課題は山済み。
・データ型の内部表現
・式の構造解析
・プリミティブな関数
・値の放棄のタイミング決定

あう゛。終わんない。
0231デフォルトの名無しさん2005/08/23(火) 22:23:09
つ Boost.Spirit
0232デフォルトの名無しさん2005/08/23(火) 22:32:35
>>231
豪華すぎ。
yaccで充分というか、あんなの自前でやるべき。
それこそlispの醍醐味というもんだろ。
0233デフォルトの名無しさん2005/08/23(火) 23:56:52
トークン切り出しはそっちのけで、内部データ構造の案。
最初はどーしよーもないんで、数、シンボル、リスト、関数型のみ扱うことにします。

#define TYPE_INT 0x00000000UL
#define TYPE_SYM 0x10000000UL
#define TYPE_LST 0x20000000UL
#define TYPE_FNC 0x30000000UL
typedef unsigned long Value;
struct Symbol { char *name; Value value; }; /* てかこれだけじゃletが扱えん・・・ */
struct Symbol symbol[1000];
struct Cell { Value car, cdr; }; /* たぶん、これだけじゃゴミ集めできん */
struct Cell list[1000];
悩む。
0234デフォルトの名無しさん2005/08/24(水) 17:50:13
[1] 授業単元:C言語基礎
[2] 問題文(含コード&リンク):http://kansai2channeler.hp.infoseek.co.jp/cgi-bin/joyful/img/872.txt
[3] 環境
 [3.1] OS:windows2k
 [3.2] コンパイラ名とバージョン:VC++6.0
 [3.3] 言語: C or C++
[4] 期限: [2005年9月01日まで]
[5] その他の制限: 特に無し
よろしくおねがいします。
0235デフォルトの名無しさん2005/08/24(水) 18:10:11
>>234
実行例見ると12と33が出現回数同じだけど、
そういうときってどうするの?
テキトーでいいの?
02362342005/08/24(水) 18:30:50
条件1に、最頻値が複数ある場合は、最も大きい値のデータを表示対象とする。とあるので
33が出るようにお願いします。わかりにくくて申し訳ないです。
0237デフォルトの名無しさん2005/08/24(水) 18:40:56
>>234
>>235ではないが。
#include <stdio.h>
int main(void) {
    int dat, dosuu[101] = {0}, num, i, max;
    printf("入力データ件数?"); scanf("%d", &num);
    num = num > 0 ? num < 20 ? num : 20 : 1;
    for (i = 0; i < num; i++) {
        printf("%2d番目の数:", i + 1); scanf("%d", &dat);
        if (0 <= dat && dat <= 100) ++dosuu[dat];
    }
    for (max = 0, i = 0; i < 101; i++) if (dosuu[max] <= dosuu[i]) max = i;
    printf("\n 最頻値:%d\n 度数:%d\n", max, dosuu[max]);
    return 0;
}
02382342005/08/24(水) 19:17:52
>>273さん
ありがとうございました。
num = num > 0 ? num < 20 ? num : 20 : 1;
の部分は学校では習っていなかったので、ここだけ
if(num > 0 && num <= 20){〜条件に合致すれば入力処理へ進む〜
}else{合致しなければおしまい
 といった形にいじらせてもらいました。では失礼します。
02392342005/08/24(水) 19:18:52
訂正、>>237さんでした・・・orz
0240デフォルトの名無しさん2005/08/25(木) 00:14:28
いんたぷりたorこんぱいらの男です。
もぉあきらめました。ご意見をくださったかた、心があたたかくなりました。
ご好意に添えないことが残念です。

友人にみせてもらって共同で作ったことにさせてもらいます・・・。
友人も出来てないみたいですが。なんとかやってくれるでしょう。
0241デフォルトの名無しさん2005/08/25(木) 02:56:28
しかし最近の高専ってレベル高いのな。
高校生とは言え宿題でコンパイラは辛いだろ。
俺だって一月でCコンパイラ作ってこい言われたらキツいぞ。
0242デフォルトの名無しさん2005/08/25(木) 03:01:36
>>241
ネットに転がってるのが前提なんじゃない?
専門学校でCASLアセンブラ作れって課題は出てたが、漏れはさっぱり分からなかった。
0243デフォルトの名無しさん2005/08/25(木) 10:36:14
yaccで逆ポーランド記法のインタプリタを作らされたことならあるぞ。
0244デフォルトの名無しさん2005/08/25(木) 22:01:23
>>243
激しく無駄だな。ワロス。
0245デフォルトの名無しさん2005/08/26(金) 00:38:48
RPNなんて7行プログラミングの管轄だろw
0246デフォルトの名無しさん2005/08/26(金) 03:29:03
7行か……#includeを書かないのが美学?
0247デフォルトの名無しさん2005/08/26(金) 14:16:05
【質問テンプレ】
[1] 授業単元:C言語�T
[2] 問題文(含コード&リンク): http://kansai2channeler.hp.infoseek.co.jp/cgi-bin/joyful/img/874.txt
[3] 環境
 [3.1] OS: Windows
 [3.2] BCC
 [3.3] 言語: C/C++/どちらでも可
[4] 期限: [2005年09月3日まで]
[5] その他の制限:特になし
どうかお願いします。
0248デフォルトの名無しさん2005/08/26(金) 14:49:08
#include <stdio.h>

int Max(int *d);
int Min(int *d);

void main()
{
int d[3],c,i;
printf("*** MAXとMIN ***\n処理件数は?: ");
scanf("%d",&c);
for(i=0;i<c;i++){
putchar('\n');
printf("調べる数値 a,b,c:");
scanf("%d,%d,%d",&d[0],&d[1],&d[2]);
printf("最大値: %d ",Max(d));
printf("最小値: %d\n",Min(d));
}
}

int Max(int *d)
{
return (d[0]<d[1])?(d[2]<d[1])?d[1]:d[2]:(d[2]>d[0])?d[2]:d[0];
}

int Min(int *d)
{
return (d[0]>d[1])?(d[2]>d[1])?d[1]:d[2]:(d[2]<d[0])?d[2]:d[0];
}
0249デフォルトの名無しさん2005/08/26(金) 16:48:05
>>247が↑のMax()とMin()の中身を理解できてるか心配。
0250≠2482005/08/26(金) 17:03:55
>>249
んじゃ、判りやすいように簡易版をw
int max2(int a, int b) {return a > b ? a : b;}
int Max(int * d)
{
return max2(max2(d[0], d[1]), d[2]);
}
int min2(int a, int b) {return a < b ? a : b;}
int Min(int * d)
{
return min2(min2(d[0], d[1]), d[2]);
}
0251デフォルトの名無しさん2005/08/26(金) 17:10:29
いけずなおまいらが大好きです
0252デフォルトの名無しさん2005/08/26(金) 17:16:25
>>251
これならどう?w
int Max(int * d)
{
int rtn = d[0];
if (d[1] > rtn) {
rtn = d[1];
}
if (d[2] > rtn) {
rtn = d[2];
}
return rtn;
}
それともこうするかw
int Max(int * d)
{
unsigned idx = 0;
if (d[1] > d[idx]) {
idx = 1;
}
if (d[2] > d[idx]) {
idx = 2;
}
return d[idx];
}
0253デフォルトの名無しさん2005/08/26(金) 17:29:29
>>247のに挑戦してたんだけど、なるだけ汎用的な
Max(int*),Min(int*)に仕上げようと思って
渡された配列の要素数を計算しようとしたのですが
sizeof(src)/sizeof(src[0])でうまく出なかったので
何でなのかと弄ってたら、srcは関数内ではあくまで配列の
先頭へのポインタでしかないからsizeof(src)してもダメなのは
当然だという所までは気づいたんですが、こういう場合
要素数はどうやって求めればいいんでしょう?
やっぱり配列を扱える方で計算した上で引数として渡すしかないんでしょうか?

srcはmain()のローカル変数として宣言してます
0254デフォルトの名無しさん2005/08/26(金) 17:39:05
int Max(valarray<int> &src) {
 return valarray.max();
};

int Min(valarray<int> &src) {
 return valarray.min();
};
0255デフォルトの名無しさん2005/08/26(金) 17:44:05
>>253
引数で渡すしかない。
C++だといろいろと回避法はあるけど。
0256デフォルトの名無しさん2005/08/26(金) 17:45:20
>>255
やっぱりそうですか・・・どうもです
0257253ではない2005/08/26(金) 18:16:24
汎用的にするならこうなるのかな
int Max(int * d, int n)
{
 int max = d[0];
 int i = 1;
 while(i < n){
  if (d[i] > max) {
   max = d[i];
  }
  i++;
 }
 return max;
}
0258デフォルトの名無しさん2005/08/26(金) 22:14:18
[1] 授業単元:
[2] 問題文:128桁までの2進数を10進数に変換する。
各Bitごとに1であれば答えとなる変数に重みを加算する、という仕様。
[3] 環境
 [3.1] OS: Windows
 [3.2] コンパイラ名とバージョン: VC 6.0
 [3.3] 言語:どちらでも可
[4] 期限: [2005年08月27日09:00まで]
[5] その他の制限: 特になし

上位Bitの数値を扱う再にオーバーフローが起きてしまいます。
その部分の解決方法についておねがいします。
0259デフォルトの名無しさん2005/08/26(金) 22:26:49
>>258
自分が作ったソースを晒しなぁ。
0260デフォルトの名無しさん2005/08/26(金) 22:29:12
>>257
俺も汎用的にしてみた。
void *max_in_array(void *a, int n, int elemsize, int(*cmp)(const void *,const void *))
{
  int i;
  char *max = a;
  char *p = ((char*)a) + elemsize;
  char *end = ((char*)a) + elemsize * n;
  for(; p < end; p += elemsize)
    if( (*cmp)(max, p) < 0 ) max = p;
  return max;
}

#define ARRAY_SIZE(a) (sizeof(a)/sizeof(*(a)))

#define MAX_IN_ARRAY(a, cmp, type) \
  ((type*)max_in_array(a, ARRAY_SIZE(a), sizeof(*(a)), cmp))

int int_cmp(const void *a, const void *b)
{
  return *(int*)a - *(int*)b;
}

int main()
{
  int x[] = {3,1,4,1,5,9,2};
  int max = *MAX_IN_ARRAY(x, int_cmp, int);
  printf("max = %d\n", max);
  return 0;
}
0261デフォルトの名無しさん2005/08/26(金) 22:34:25
>>260
無駄にそこまでこるならC++でテンプレート使えばいいじゃない。
02622582005/08/26(金) 22:39:42
http://kansai2channeler.hp.infoseek.co.jp/cgi-bin/joyful/img/875.txt

もともと32桁16進→10進という課題だったため、前半部分で16→2にしています。
作りかけでいろいろ無駄がありますが目をつぶってください。
0263デフォルトの名無しさん2005/08/26(金) 23:00:28
>>262
403 forbidden
0264デフォルトの名無しさん2005/08/26(金) 23:15:34
>>262
要は途中でunsined longなりの最大値超えるからでしょ?
適当な要素数のint型配列つかって10進数を表して
そいつを表示する部分と、乗算する部分作った方がいい希ガス

とりあえず自分で作ろうと思ってた奴の表示と乗算の部分だけ完成させたから
参考にでもしてくれ
ttp://kansai2channeler.hp.infoseek.co.jp/cgi-bin/joyful/img/876.txt
0265デフォルトの名無しさん2005/08/27(土) 00:33:47
>>262
いろいろ目をつぶったら何も見えなくなった。
って後半(2->10)も何もないじゃないかあ〜!
(後、結果の保持or出力の形式の条件(有無さえ)が不明だなあ。
128桁の2進数値の保持に 128bit以上の整数型が必要になるのは理解済み?)
0266デフォルトの名無しさん2005/08/27(土) 01:55:38
そのあたりは理解しています。
数値ではなく、文字として処理して計算?という案はあるのですが
加算処理をどう表現していいのかがわからず、です。

計算結果はそのまま 123456798456132・・・というふうに表示し、プログラム終了です。
0267デフォルトの名無しさん2005/08/27(土) 02:17:58
>>266
文字として処理っていうのは筆算での掛け算をするってことか?
02682582005/08/27(土) 02:37:59
桁数が大きくなると、普通に数値として計算ができなくなるので
数字の足し算を文字と文字の組み合わせで表現すればいいのでは?と考えてました。
1と1が組み合わさるときは2、1と2が組み合わさるときは3・・・とパターンを決めて計算を表現するということです。
うまく説明できない・・・
とりあえず、普通の足し算を行うのはあきらめる気でいました。
0269デフォルトの名無しさん2005/08/27(土) 02:40:10
>>266
> 数値ではなく、文字として処理して計算?という案
10進数の数値に対して 1桁に1バイト割り当て&その値空間が '0' 〜 '9' ってことか?
02702582005/08/27(土) 02:48:51
>>269
まさにそのとおりです。


と、ここまで書いておいて別の方法に気がつきました。
大きな数を4桁ずつとかに区切り、配列に格納したモノ同士を足していくほうが
繰り上がりの問題も含めて単純に解決できそうです。
今まで考えでは1桁ずつ計算していましたが、こちらのほうが楽かつ簡単な気がします。

考えがまとまらずにフラフラしてしまって申し訳ありません。
なかなかうまく進まず焦ってしまっています。
一旦自分で考え直してもう一度質問すべきことを練り直します。
0271デフォルトの名無しさん2005/08/27(土) 03:13:40
[1] 授業単元: プログラミング演習
[2] 問題文(含コード&リンク): バイナリのファイルを4byeづつ読み込んでヒストグラムを求める。
[3] 環境
 [3.1] OS: Linux
 [3.2] gcc
 [3.3] 言語: C
[4] 期限: [2005年8月28日12:00まで]
[5] その他の制限:

問題文ではなく口頭で言われたので、言葉足らずのところがあると思いますが、
よろしくお願いいたします。
口頭では、「例えば、12バイトのバイナリファイルがあったとする。
そのファイルを4バイトずつ読み込み、それらを十進法であらわすと100、200、100だったとする
するとヒストグラムは(もちろん2の128乗の場合があるわけで出現してないものも表記すること)
0  |
1  |
・  |
・  |
100|**
200|*
(あとは省略)となる。 2の128乗の場合があるわけでターミナルに上のように表すのはどうかと思うので
エクセルなどでヒストグラムを作れるようにすること。といわれました。どうかよろしくお願いいたします。

0272デフォルトの名無しさん2005/08/27(土) 04:00:59
いちおう確認させてもらう。

習ったデータ構造は?(2分探索木、ハッシュ、mallocする形の二次元配列)
習ったバイナリファイルを読み込む方法は?
出力はアスタリスクの横棒とエクセルファイル、どちらを作ればいいの?
0273デフォルトの名無しさん2005/08/27(土) 04:28:11
>>271
普通にバイナリモードで開いて、freadでunsigned longの変数に
放り込めばよくないか?
0274デフォルトの名無しさん2005/08/27(土) 04:41:58
俺の教科書だと、
unsigned long x;
x = (getchar() & 0xff) << 24;
x |= (getchar() & 0xff) << 16;
x |= (getchar() & 0xff) << 8;
x |= (getchar() & 0xff);
ってなっとる(爆) これもなんだかな・・・だが。

unsigned longが64ビットじゃない処理系って、俺は知らんけど、
fread(&x, 4, fp)とかだと、処理系依存じゃねぇか?
■ このスレッドは過去ログ倉庫に格納されています