• ベストアンサー

C言語の問題

自分の生まれた日から、今日までの生存日数を求めよ。(但し、うるう年なども計算するプログラム)という問題を提示されたのですが、ぜんぜんわかりません。どなたか上記プログラムがわかる方、ご教授お願いいたします。 #include<stdio.h> int main(void) { int table1[13]={0,31,28,31,30,31,30,31,31,30,31,30,31}; int table2[13]={0,31,29,31,30,31,30,31,31,30,31,30,31}; int mm,dd,i,day=0; /*(1)指定月日までの日数計算*/ do { printf("月>"); scanf("%d",&mm); if(mm>=1 && mm<=12)break; printf("月(%d)は誤りです。\n",mm); }while(1); do { printf("日>"); scanf("%d",&dd); if(dd>=1 && dd<=table1[mm])break; printf("日(%d)は誤りです。\n",dd); }while(1); for(i=1;i<mm;i++) day += table1[i]; day += dd; printf("1/1から%d/%d迄の日数は%d日です。\n",mm,dd,day); return 0; } ↑参考までにこんなプログラムでやっています。

  • svst
  • お礼率62% (65/104)

質問者が選んだベストアンサー

  • ベストアンサー
  • essential
  • ベストアンサー率100% (1/1)
回答No.4

No.3 の人に近い?ですが、1970年1月1日以降に生まれた人なら 次のようなものでもOKですよ。 #include <stdio.h> #include <time.h> void main( void ) { int year = 0; int mon = 0; int day = 0; time_t timer; struct tm t; /* 現在時刻の取得 */ time(&timer); /* 自分の生年月日(年月日:19871231)を入力 */ scanf( "%4d%02d%02d" ,&year, &mon, &day ); memset( &t, 0, sizeof( struct tm ) ); t.tm_year = year - 1900; t.tm_mon = mon - 1; t.tm_mday = day; /* 構造体を秒に変換 */ if( ( timer = mktime( &t ) ) == -1 ) { printf( "生年月日が変です\n " ); exit( 0 ); } /* 現在時刻との差分をとる */ timer = time( 0 ) - timer; printf( "生存日数は %d 日です\n", timer / ( 24 * 60 * 60 ) ); }

svst
質問者

お礼

わざわざ、プログラム本体を掲載してもらい非常に参考になります。 ありがとうございました。 1つ、質問ですがこのプログラムは閏年を計算しているのでしょうか。 (ぱっと見るとちょっと分からないのですが、教えていただけると幸いです)

その他の回答 (5)

  • rentahero
  • ベストアンサー率53% (182/342)
回答No.6

#4のプログラムについて > 1つ、質問ですがこのプログラムは閏年を > 計算しているのでしょうか。 計算するまでもなく、time関数はうるう年計算を内蔵しているから大丈夫です。 しかし、問題点は、time_tがsigned longの場合、1901年12月15日~2038年1月19日までしかうまく動かないという点です。 ということで、正しくは真っ向から計算するべきですね。

svst
質問者

お礼

time関数はうるう年計算を内蔵している事は知りませんでした。 勉強になりました。 アドバイス有難うございました。

  • BLUEPIXY
  • ベストアンサー率50% (3003/5914)
回答No.5

/* 基準日:西暦1年1月1日(月)を基準に日付の計算をする */ #include <stdio.h> #include <stdlib.h> #include <time.h> int isLeapYear(unsigned y){ return ((0 == y % 400)||((0 == y % 4)&&(0 != y % 100))); } unsigned leapDays(unsigned y){ /* 基準日から指定年までの閏日の日数 */ return (y/4 - y/100 + y/400); } unsigned daysFromYearTop(unsigned y, unsigned m, unsigned d){ /* 指定日の年頭からの日数 */ static unsigned daysOfMonth[]={ NULL, 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334 }; return (daysOfMonth[m]+((m>2 && isLeapYear(y))? 1:0) + d); } unsigned long days(unsigned y, unsigned m, unsigned d){ /* 基準日から指定日までの通算日数 */ unsigned lastYear=y-1; return(leapDays(lastYear) + lastYear*365 + daysFromYearTop(y, m, d)); } int main(void){ unsigned y, m, d; unsigned long todays, birthday; struct tm *today; time_t now; now=time(NULL); today=localtime(&now); y=today->tm_year + 1900; m=today->tm_mon + 1; d=today->tm_mday; todays=days(y,m,d); birthday=days(1945,8,15); /* 1945/8/15日生まれ */ printf("生存日数:%lu\n",todays-birthday);/* 生まれたその日は0 */ return(EXIT_SUCCESS); }

svst
質問者

お礼

わざわざ、プログラム本体を掲載してもらってありがとうございます。 今後の参考にさせて頂きます。

  • vivlet
  • ベストアンサー率36% (24/66)
回答No.3

問題点は先のお二人のお返事にありますから、別の視点で。 二つの日付間の日数を求めるには、ユリウス日や準ユリウス日に変換して算出すると楽ですよ。 ユリウス日とは、紀元前4713年1月1日からの連続した通し番号の日数で 準ユリウス日は、1858年11月17日0時(世界標準時)です。 プログラム方ですが 1.生年月日入力 2.現在日付取得 3.生年月日を準ユリウス日に変換 4.現在日付を準ユリウス日に変換 5. 4 と 3 の差を求める になりますね。 詳しい説明や変換方法は参考URLで

参考URL:
http://homepage1.nifty.com/manome/astrology/julian.html
svst
質問者

お礼

アドバイスをして頂き、有難うございました。 参考URLを教えていただき、非常に助かります。

  • ymmasayan
  • ベストアンサー率30% (2593/8599)
回答No.2

年のことが考えてありませんね。 生存日数ですから18歳なら6000日以上の日数になるはずです。 生まれた年の誕生日から今日までということです。

svst
質問者

お礼

アドバイスをして頂き、有難うございました。 確かに、年数が抜けていました。 再構築をしてみます。

  • trajaa
  • ベストアンサー率22% (2662/11921)
回答No.1

ぱっと見て ・年については何も処理が無い ・年が不明なので閏年の判定も無い ・1/1から指定日付までの日数は計算している ・指定日付が生年月日なら、指定日付から12/31迄の日数を求めなければならないのでは? ・今日という日付はどこにも無い という感じで、基本的な部分が不足・誤解しているようです。 まずは、日本語(フローチャートが書けるならそちら)で、何が必要な情報で、どういった手順で処理を実行していくのかを、書き出してみてください。 その後、その日本語をソースコードに置き換えていくイメージで。

svst
質問者

お礼

アドバイスを、有難うございます。 フローチャートを書いてから、再度トライしてみようと思います。

関連するQ&A

  • C言語 switch文について

    C言語初心者です。 以下のようにC言語でプログラムを書いてみたのですが、 一つの入力に対して、対応するcase文に加えてdefault部の内容も表示されてしまいます。 (aを入力すると day before yesterday と day after tomorrowが表示されるような感じです) i,j,k などを使ってどう実行されているかを調べると、どうやら一回の入力に対して二回switch部を回っているようです。 そうにしろなぜaに対してdefaultへ飛ぶのか理解できませんが・・ また、最初の宣言をchar から int にして(caseは、case 1とかに適当に変えて)やると、正常に動くのも不可解です。 どうなっているんでしょうか・・ どなたかご教授願えると幸いです。よろしくお願いいたします。 #include <stdio.h> int main(void) { char n; int i=0,j=0,k=0; k++; while(scanf("%c",&n),n!='E'){ i++; switch(n){ case 'a': puts("day before yesterday"); break; case 'b': puts("yesterday"); break; case 'c': puts("today"); break; case 'd': puts("tomorrow"); break; default: puts("day after tomorrow"); break; j++; } } printf("%d\n",i); printf("%d\n",j); printf("%d\n",k); return 0; }

  • C言語の問題がわからないです。

    C言語のプログラムで、列数を自分で決めて、 (例)3列         ●(この行を最後として)   □● ●□● 上記のプログラムを作りたいのですが、 上手くいきません。途中まで作ったのですが、なかなか思うようにいかないです。どうすれば上記のようになりますでしょうか? #include <stdio.h> void disp(int x, int y); main() { int i,n; printf("表示する列:"); scanf("%d",&n); disp(3,3); for(i=1;i<=n;i++){ if(i%2==0){ disp(n-i,4); disp(i,2); } else{ disp(n-i,4); disp(i,1); } disp(1,3); } } void disp(int x, int y) { int i; for(i=0;i<x;i++){ if(y==1){ printf("●"); } else if(y==2){ printf("□"); } else if(y==3){ printf("\n"); } else{ printf("\0"); } } }

  • C言語の四則演算プログラムについて

    こんにちは。hayato2192といいます。 今回は、C言語についてのことを質問したいとおもいます。 MSN相談箱の質問の中で数ある四則演算プログラムに対する質問をみたのですが、僕がつくろうとしているプログラムとはまったくちがいました。 プログラムコードは以下です。 \\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\ #include <stdio.h> main() { int d1, d2; char op; printf("START PROGRAM : Arithmetic operation\n"); printf("ENTER THE NUMBER\n"); scanf(" %d", &d1); printf("ENTER THE OPERATOR\n"); scanf(" %c", &op); switch (op) { case '+': printf("ENTER THE NUMBER\n"); scanf(" &d", &d2); printf("ANSWER IS %d\n", d1+d2); break; case '-': printf("ENTER THE NUMBER\n"); scanf(" &d", &d2); printf("ANSWER IS %d\n", d1-d2); break; case '*': printf("ENTER THE NUMBER\n"); scanf(" &d", &d2); printf("ANSWER IS %d\n", d1*d2); break; case '/': printf("ENTER THE NUMBER\n"); scanf(" &d", &d2); printf("ANSWER IS %d\n", d1/d2); break; default: printf("NO ANSWER\n"); break; } return 0; } \\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\ 使っている関数はscanf printf switchだけというとてもシンプルなプログラムなのです。 じっさい、このプログラムをBorlandのコンパイラでコンパイルすると、switch関数がまったく使われずに、演算子(このプログラムでいうOPERATORです)を入力するところで終了してしまいます。 どのように直せばよいのでしょうか。教えてください

  • C言語のswitch文について間違っているところを教えてください

    初めに初心者ですので間違っているところは説明つきの回答をしていただければありがたいです。 今回switch文を使って 「足し算、引き算、掛け算、割り算」のプログラムを作ったつもりなのですが、intを使うと割り算の小数点が出ないしfioat文を使うとswitch文には、使えないと出るしどのようにしたら良いのか御回答よろしくお願いします。 (今は、int文でプログラムを作っているつもりです。) #include <stdio.h> void main (void) { int a,b,k; printf("どのような計算をしたいか数字を選んでください。\n"); printf(" 1.足し算 (例 a+b)\n"); printf(" 2.引き算 (例 aーb)\n"); printf(" 3.掛け算 (例 a×b)\n"); printf(" 4.割り算 (例 a÷b)\n"); printf("計算したい番号を入力してください "); scanf("%d",&k); switch (k){ case 1: printf("aを入力してください "); scanf("%d",&a); printf("bを入力してください "); scanf("%d",&b); printf("\n答えは a+b で %d です\n",a+b); break; case 2: printf("aを入力してください "); scanf("%d",&a); printf("bを入力してください "); scanf("%d",&b); printf("\n答えは aーb で %d です\n",a-b); break; case 3: printf("aを入力してください "); scanf("%d",&a); printf("bを入力してください "); scanf("%d",&b); printf("\n答えは a×b で %d です\n",a*b); break; case 4: printf("aを入力してください "); scanf("%d",&a); printf("bを入力してください "); scanf("%d",&b); printf("\n答えは a÷b で %d です\n",a/b); break; default: printf("明記してあるどれかの数字を再入力してください"); } }

  • C言語の穴埋め問題なのですが

    ???の中身を教えてください #include <stdio.h> #define N 3 //構造体の宣言 typedef struct date{ char *nengou; int year; int month; int day; }DATE; //関数のプロトタイプ宣言 void disp(DATE data); int main(void) { DATE birthday; char buff[80]; ???= buff; printf("年号:"); scanf("%s" , birthday.nengou); printf("年:"); scanf("%d" ,&birthday.year ); printf("月:"); scanf("%d" , &birthday.month); printf("日:"); scanf("%d" ,&birthday.day ); disp(birthday ); } void disp(DATE data) { printf("%s%d年%d月%d日\n" , data.nengou , data.year , data.month , data.day); }

  • C言語

    #include <stdio.h> int main(void) { int month, days; puts("月を入力してください:"); scanf("%d",&month); // if(month == 2) days = 28; if (month == 1 || month == 3 || month == 5 || month == 7 || month == 8 || month == 10 || month == 12); days = 31; else days=30; printf("%d月は%d日あります。\n", month, days); return(0); } // 月と日数の場合わけをしたいのですがうまくいきません。どこをなおせばいいのか誰か教えてください!

  • C言語

    #include <stdio.h> int main(void) { int month, days; puts(\"月を入力してください:\"); scanf(\"%d\",&month); // if(month == 2) days = 28; if (month == 1 || month == 3 || month == 5 || month == 7 || month == 8 || month == 10 || month == 12); days = 31; else days=30; printf(\"%d月は%d日あります。\\n\", month, days); return(0); } // 月と日数の場合わけをしたいのですがうまくいきません。どこをなおせばいいのか誰か教えてください!

  • C言語の問題

    以下はC言語の問題です。お教えください。 1000以下の素数を求めるプログラム prog.c を作成せよ。各素数を整数4桁で出力し、15個の素数を出力した時点で改行処理 を行うこと。作成したプログラムを提出せよ。 です。 僕の考えでは、 #include <stdio.h> #include <math.h> main(){ int i; int j; int ix; int k; printf("正の整数を入力して下さい: "); scanf("%d",&i); ix=(int)(sqrt((double)i)); k=0; for(j=2;j<=ix;j++) { if(i%j==0) { k=1; } } if(k==0) { printf("%d は素数です\n",i); } else { printf("%d は素数ではありません\n",i); } となると思うのですが。どうやら違うようです。全然わからないので、正しい答えを教えてください。

  • C言語で分からないところがあるのですが……

    C言語で分からないところがあるのですが…… すみません。C言語を学習していてつまづいたので、皆さんの意見を聞きたいと思います。 現在、カレンダーを表示するプログラムをつくっています。 Yearとmonthをユーザが入力すると、その年その月のカレンダーが出るという算段です。(画像貼っておきます。ソースコードは下) これはできました。 これをいじって、Yearをユーザから受け取ると、その年の1月から12月までのカレンダーがば~っと表示されるようにしろ、と言われました。 Yearとmonthを受け取って書くやつは友人の助けを得ながらなんとかかけましたが、もう無理です。多分、for文を使うんだと思うんですが……助けてください! #include <stdio.h> int dayofweek(int year, int month); int daysinmonth(int year, int month); int daysinyear(int year); void showcal(int dow, int days); int main(void) { int year, month; int dow; int dim; printf ("Year?: "); scanf ("%d", &year); printf ("Month?: "); scanf ("%d", &month); dow = dayofweek(year, month); dim = daysinmonth(year, month); showcal(dow, dim); return 0; } void showcal (int dow, int days) { int i, j, d; printf ("Su Mo Tu We Th Fr Sa\n"); d = 1; for (i = 0; i < dow; i++) { printf (" "); } for (; i < 7; i++) { printf (" %d ", d); d++; } printf("\n"); for (j = 0; d <= days; j++) { for (i = 0; i < 7 && d <= days; i++) { if (d < 10) printf (" %d ", d); else printf ("%d ", d); d++; } printf("\n"); } } int daysinmonth( int year, int month) { int dim; dim = 31; if (month == 4 || month == 6 || month == 9 || month == 11) dim = 30; if (month == 2) { if ( (year % 4 == 0 && year % 100 != 0) || year % 400 == 0) dim = 29; else dim = 28; } return dim; } int daysinyear( int year) { int diy; if ( (year % 4 == 0 && year % 100 != 0) || year % 400 == 0) diy = 366; else diy = 365; return diy; } int dayofweek (int year, int month) { int dow; int days; int y, m; if (year >= 2000) { days = 0; for ( y = 2000; y < year; y++ ) { days = days + daysinyear(y); } for ( m = 1; m < month; m++ ) { days = days + daysinmonth(year, m); } dow = (6 + days) % 7; } else { days = 0; for ( m = month; m <= 12; m++ ) { days = days + daysinmo

  • C言語の課題で

    C言語の課題で 「成績集計プログラム 入力件数nをキーボードより入力し、n人分のテストデータを入力する。その際、合計点、最高点、最低点を求め、最後に平均点を計算しそれぞれを出力するプログラムを作成せよ。ただし、平均点は実数型とし小数点第2位まで出力する。平均点以外の変数は整数型とする。」というのが出ました。 #include <stdio.h> int main(void) { int n,a,b,c; int res,i; printf("入力件数を入力して下さい。\n"); scanf("%d",&n); for(i = 1; i <= n; i++) { printf("点数を入力して下さい。\n"); scanf("%d",&a); printf("%d人目=>%d\n",i,a); if(i == res) break; } return 0; } ここまでは、出来たのですが、後が分かりません。どなたか教えていただけませんか?お願いします。

専門家に質問してみよう