質問をすることでしか得られない、回答やアドバイスがある。

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

新規登録して質問してみよう
ただいま回答率
85.50%
C

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

Q&A

解決済

3回答

398閲覧

「実行時間の新しい順」にソートしたいのですが、上手くいかない

退会済みユーザー

退会済みユーザー

総合スコア0

C

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

0グッド

0クリップ

投稿2017/09/27 02:02

「実行時間の新しい順」にソートしたいのですが,2017年と2016年の間に2014年が表示されて、上手くいきません。どこが悪いのか分からないので教えてください。

//qsort で構造体のポインタ配列をソートする例 //TIME_DATA型(年,月,日,時,分,秒,秒) //この各要素を指すポインタの配列を用意して、「実行時間の新しい順に」 qsort します。 //jikan_sort-3.c #include <stdio.h> #include <stdlib.h> #include <time.h> #define MAXCNT 100 char dtfile[]="LACKNUM.DAT"; typedef struct // 構造体の宣言 { int tm_year; int tm_mon; int tm_mday; int tm_hour; int tm_min; int tm_sec; double score; }TIME_DATA; int cmp(const void *a1, const void *b1) { long asum, bsum; const TIME_DATA *a = (const TIME_DATA*)a1; const TIME_DATA *b = (const TIME_DATA*)b1; asum = a->tm_year * 10000000000L + a->tm_mon * 100000000L + a->tm_mday * 1000000L + a->tm_hour * 10000L + a->tm_min * 100L + a->tm_sec; bsum = b->tm_year * 10000000000L + b->tm_mon * 100000000L + b->tm_mday * 1000000L + b->tm_hour * 10000L + b->tm_min * 100L + b->tm_sec; if (asum > bsum) return -1; else if (asum < bsum) return 1; return 0; } int main(void) { int i,count,n; FILE *fp; TIME_DATA lst[MAXCNT]; // 構造体の宣言 if((fp=fopen(dtfile, "rb")) == NULL ) { printf( "ファイルがオープンできません\n"); exit( 1 ); } i=count=0; while (fscanf(fp,"%d %d %d %d %d %d %lf" // 構造体配列への読み込み , &lst[i].tm_year,&lst[i].tm_mon,&lst[i].tm_mday, &lst[i].tm_hour,&lst[i].tm_min,&lst[i].tm_sec, &lst[i].score )!= EOF){ i++; count++; } n=count; qsort(lst,n, sizeof(TIME_DATA), cmp); printf("count:%d\n",count); printf( "■並べ替え前\n" ); for(i=0; i<count; i++){ printf("%4d年 %2d月 %2d日 %2d時 %2d分 %2d秒 \n所要時間(score):%.1f\n\n", // 構造体配列への読み出し lst[i].tm_year,lst[i].tm_mon,lst[i].tm_mday, lst[i].tm_hour,lst[i].tm_min,lst[i].tm_sec,lst[i].score); } // 並べ替え qsort(lst, count, sizeof (TIME_DATA), cmp); // 並べ替え後表示 printf( "■並べ替え後\n" ); for(i=0; i<count; i++){ printf("%4d年 %2d月 %2d日 %2d時 %2d分 %2d秒 \n所要時間(score):%.1f\n\n", // 構造体配列への読み出し lst[i].tm_year,lst[i].tm_mon,lst[i].tm_mday, lst[i].tm_hour,lst[i].tm_min,lst[i].tm_sec,lst[i].score); } fclose(fp); printf("count1:%d\n\n", count); return 0; } /* C:\MinGW\users\chap09\kadai>gcc -I. -o jikan_sort-3 jikan_sort-3.c -Wall C:\MinGW\users\chap09\kadai>jikan_sort-3 NDATA:13 C:\MinGW\users\chap09\kadai>jikan_sort-3 count:13 ■並べ替え前 2017年 9月 16日 8時 18分 10秒 所要時間(score):8.6 2017年 9月 14日 10時 21分 18秒 所要時間(score):6.0 ...... ■並べ替え後 2017年 9月 16日 8時 18分 10秒 所要時間(score):8.6 2017年 9月 14日 10時 21分 18秒 所要時間(score):6.0 2017年 9月 6日 8時 18分 9秒 所要時間(score):10.6 2014年 2月 12日 28時 31分 49秒 所要時間(score):13.0 2014年 1月 4日 23時 43分 50秒 所要時間(score):10.2 2016年 8月 7日 22時 31分 52秒 所要時間(score):9.3 2016年 5月 31日 21時 9分 53秒 所要時間(score):7.0 2016年 4月 5日 19時 16分 8秒 所要時間(score):9.0 2016年 2月 28日 2時 27分 20秒 所要時間(score):7.8 ........ count1:13 C:\MinGW\users\chap09\kadai> */

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

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

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

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

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

guest

回答3

0

C

1long asum, bsum;

ここなのですが、Cのlongは4byteで動作するのが一般的であり、4byte符号付き整数型の最大値は2,147,483,647です。ところがあなたの処理では年を10,000,000,000倍しており、一気に桁あふれを起こしています。なので、asumbsumは予期しないわけの分からない数字になっている可能性が高いです。
型をlong longにするべきかと思います。そうすれば9,223,372,036,854,775,807まで使えるので、桁あふれしないでしょう。

投稿2017/09/27 02:16

masaya_ohashi

総合スコア9206

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

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

退会済みユーザー

退会済みユーザー

2017/09/27 09:12

masaya_ohashiさんありがとうございます。みなさんのお助けで次に進めます。
guest

0

ベストアンサー

あれ、これは私の回答 https://teratail.com/questions/94011 がバグってた?
オリジナルのコード実行結果とqsort()版の実行結果とでdiff取って確認したんだけどなぁ…

で、思いついたのは、私はmacOSで実行してたので LP64、つまりlongは64bitなんです。

long longにするのが正解でしたね。すみません。

投稿2017/09/27 02:35

daisuke7

総合スコア1563

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

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

0

値がオーバーフローしているんだと思います。
次のように書いたら上手く動作しました。

C

1unsigned long long get_value(const TIME_DATA *time_datum); 2 3int cmp(const void *arg1, const void *arg2) 4{ 5 unsigned long long 6 sum1 = get_value((const TIME_DATA *)arg1), 7 sum2 = get_value((const TIME_DATA *)arg2); 8 9 if (sum1 > sum2) return -1; 10 else if (sum1 < sum2) return 1; 11 else return 0; 12} 13 14unsigned long long get_value(const TIME_DATA *time_datum) { 15 return time_datum->tm_year * 10'000'000'000L 16 + time_datum->tm_mon * 100'000'000L 17 + time_datum->tm_mday * 1'000'000L 18 + time_datum->tm_hour * 10'000L 19 + time_datum->tm_min * 100L 20 + time_datum->tm_sec * 1L; 21}

投稿2017/09/27 02:19

LouiS0616

総合スコア35658

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

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

退会済みユーザー

退会済みユーザー

2017/09/27 09:19

LouiS0616さんありがとうございます。助かっています。初心者ですので桁の表示をそのまま入れて、 手間取りました。わかり易いように入れてくだっさたのですね。これから今までのコードをリンクして、 1つのコードにしたいと思います。エラーが出るとおもいますがその時はまたお願いいたします。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.50%

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

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

質問する

関連した質問