Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <iostream>
- #include <iomanip>
- #include <string>
- // Forward declarations for functions we'll use later (these could have easily just been put in
- // this order at the top of this source file):
- bool is_leap_year(const short year);
- std::string month_name(const short month);
- short days_in_month(const bool is_leap_year, const short month);
- void print_whitespace(const size_t amount);
- void print_calendar(const bool is_leap_year, const short calendar[12][31]);
- void generate_calendar(const bool is_leap_year, const short start_day, short calendar[12][31]);
- int main(int /*argc*/, char* /*argv*/[])
- {
- short year = 0;
- short day = 0;
- bool day_valid = false;
- // Get user input for year and validate it.
- while(!year)
- {
- std::cout << "Enter the year: ";
- std::cin >> year;
- if(year < 0 || year > 9999)
- {
- std::cout << "That's not a valid year!" << std::endl;
- year = 0;
- }
- }
- // Get user input for day and validate it.
- while(!day_valid)
- {
- std::cout << "Enter the day of the week of January 1st, using 0 through 6" << std::endl
- << "(eg. 0 = Sun, 1 = Mon, 2 = Tue, 3 = Wed, 4 = Thu, 5 = Fri, 6 = Sat): ";
- std::cin >> day;
- if(day < 0 || day > 6)
- std::cout << "That's not a valid day! Must be between 0 and 6." << std::endl;
- else
- day_valid = true;
- }
- // The assignment seems to require this.
- const bool leap_year = is_leap_year(year);
- if(leap_year)
- std::cout << year << " is a leap year." << std::endl
- << "There are 29 days in February." << std::endl;
- else
- std::cout << year << " is not a leap year." << std::endl
- << "There are 28 days in February." << std::endl;
- // Generate our calendar.
- short calendar[12][31];
- generate_calendar(leap_year, day, calendar);
- print_calendar(leap_year, calendar);
- return EXIT_SUCCESS;
- }
- bool is_leap_year(const short year)
- {
- // A year is a leap year if it is divisible by 4 unless it is both divisible by 100 and not divisible by 400.
- if(year%4==0)
- {
- if(year%100==0 && year%400!=0)
- return false;
- return true;
- }
- return false;
- }
- std::string month_name(const short month)
- {
- switch(month)
- {
- case 0:
- return "January";
- case 1:
- return "February";
- case 2:
- return "March";
- case 3:
- return "April";
- case 4:
- return "May";
- case 5:
- return "June";
- case 6:
- return "July";
- case 7:
- return "August";
- case 8:
- return "September";
- case 9:
- return "October";
- case 10:
- return "November";
- case 11:
- return "December";
- }
- return "WTF"; // I usually use a NODEFAULT() macro. This code will never be executed.
- }
- short days_in_month(const bool is_leap_year, const short month)
- {
- short days_count = 0;
- switch(month)
- {
- // 30 days has september, april, june, and november. all the rest have 31, except for
- // february, 28! Or friggin 29 on a leap year.
- case 8: case 3: case 5: case 10:
- days_count = 30;
- break;
- case 1:
- if(is_leap_year)
- days_count = 29;
- else
- days_count = 28;
- break;
- default:
- days_count = 31;
- }
- return days_count;
- }
- void print_whitespace(const size_t amount)
- {
- // Printing spaces for formatting becomes a common thing we do, so we want to put it in a
- // function that handles it.
- for(size_t i=0;i<amount;++i)
- std::cout << " ";
- }
- void print_calendar(const bool is_leap_year, const short calendar[12][31])
- {
- for(short month = 0; month < 12; ++month)
- {
- // Print the calendar header. Note that the whole calendar, including the '+' signs, is
- // TWENTY FOUR CHARACTERS LONG.
- std::cout << "+----------------------+" << std::endl
- << "|";
- // We want to make the month name nicely centered in the calendar month heading. I'd usually
- // use std::setw here like we do below for the days, but that would require iostreams to have
- // a "std::center" (similar to how it has a std::left and std::right), but it doesn't. So we
- // need to do it ourselves.
- const std::string mn = month_name(month);
- const size_t left_ws = (22-mn.length())/2 + mn.length()%2;
- const size_t right_ws = (22-mn.length())/2;
- print_whitespace(left_ws);
- std::cout << mn;
- print_whitespace(right_ws);
- std::cout << "|" << std::endl;
- std::cout << "+----------------------+" << std::endl
- << "| S M T W T F S |" << std::endl
- << "+----------------------+" << std::endl
- << "|";
- // The first line of the calendar is a bit special - it has some empty days. Print each empty
- // day (they're three spaces each).
- short day = calendar[(size_t)month][(size_t)0];
- print_whitespace(day*3);
- // Iterate through the rest of the days.
- const short days_count = days_in_month(is_leap_year, month);
- for(short date = 0; date < days_count; ++date)
- {
- std::cout << std::right << std::setw(3) << date+1;
- if(7 == ++day)
- {
- day = 0;
- std::cout << " |" << std::endl
- << "|";
- }
- }
- // Similarly to the first line (but backwards), print the trailing whitespace.
- print_whitespace((7-day)*3);
- std::cout << " |" << std::endl
- << "+----------------------+" << std::endl
- << std::endl;
- }
- }
- void generate_calendar(const bool is_leap_year, const short start_day, short calendar[12][31])
- {
- short day = start_day;
- for(short month=0; month < 12; ++month)
- {
- const short days_count = days_in_month(is_leap_year, month);
- for(short date=0; date < days_count; ++date)
- {
- if(7 == day)
- day = 0;
- calendar[(size_t)month][(size_t)date] = day++;
- }
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement