Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <stdio.h>
- #include <ctype.h>
- #include <stdlib.h>
- #define MIN_YEAR 1600
- #define MAX_YEAR 2399
- #define YEAR_OFFSET 2000
- #define RV_NODATE 0
- #define RV_VALIDDATE 1
- #define RV_INVALIDDATE 2
- #define RV_START 3
- #define RV_MONTH_1 4
- #define RV_MONTH_2 5
- #define RV_DAY_0 6
- #define RV_DAY_1 7
- #define RV_DAY_2 8
- #define RV_YEAR_0 9
- #define RV_YEAR_1 10
- #define RV_YEAR_2 11
- #define RV_YEAR_3 12
- //#define RV_YEAR_4 13
- #define MONTH_STATE 0
- #define DAY_STATE 1
- #define YEAR_STATE 2
- /***** DFA *****/
- /* The function checks if a date is present at the beginning of a line,
- * and if the date is valid.
- *
- * Return values:
- *
- * 0: Not date was found.
- * 1: Date is valid.
- * 2: Date was found, but not valid.
- */
- int validate_date(int month, int day, int year) {
- int output = 0;
- int leapYear = 0;
- switch ((year % 400 == 0) || ((year % 4 == 0) && (year % 4 != 0))) {
- case 1:
- leapYear = 1;
- break;
- case 0:
- default:
- break;
- }
- switch (month){
- case 1:
- case 3:
- case 5:
- case 7:
- case 8:
- case 10:
- case 12:
- switch (day <= 31) {
- case 1:
- output = 1;
- break;
- case 0:
- default:
- output = 0;
- break;
- }
- break;
- case 4:
- case 6:
- case 9:
- case 11:
- switch (day <= 30) {
- case 1:
- output = 1;
- break;
- case 0:
- default:
- output = 0;
- break;
- }
- break;
- case 2:
- switch (leapYear) {
- case 1:
- switch (day <= 29) {
- case 1:
- output = 1;
- break;
- case 0:
- default:
- output = 0;
- break;
- }
- break;
- case 0:
- switch (day <= 28) {
- case 1:
- output = 1;
- break;
- case 0:
- default:
- output = 0;
- break;
- }
- break;
- }
- break;
- default:
- output = 0;
- break;
- }
- return output;
- }
- int get_date() {
- int state;
- int ch;
- int month = 0;
- int day = 0;
- int year = 0;
- int expectingDash = 0;
- int canAcceptDash = 0;
- int dateState = 0;
- int acceptChar = 0;
- state = RV_START;
- ch = getchar();
- while (ch != '\n' && ch != EOF) {
- switch (isdigit(ch)) {
- case 2048:
- switch (state) {
- case RV_START:
- dateState = MONTH_STATE;
- state = RV_MONTH_1;
- month += (ch - '0');
- canAcceptDash = 1;
- break;
- case RV_MONTH_1:
- state = RV_MONTH_2;
- month = (month * 10) + (ch - '0');
- switch (month > 12) { //check if months are valid
- case 1:
- //state = RV_INVALIDDATE;
- break;
- default:
- expectingDash = 1;
- break;
- }
- break;
- case RV_DAY_0:
- dateState = DAY_STATE;
- state = RV_DAY_1;
- day += (ch - '0');
- canAcceptDash = 1;
- break;
- case RV_DAY_1:
- state = RV_DAY_2;
- day = (day * 10) + (ch - '0');
- switch (day > 31) { //checking if days are valid
- case 1:
- state = RV_VALIDDATE;
- break;
- default:
- expectingDash = 1;
- break;
- }
- break;
- case RV_YEAR_0:
- state = RV_YEAR_1;
- dateState = YEAR_STATE;
- year += (ch - '0');
- break;
- case RV_YEAR_1:
- state = RV_YEAR_2;
- year = (year * 10) + (ch - '0');
- break;
- case RV_YEAR_2:
- state = RV_YEAR_3;
- year = (year * 10) + (ch - '0');
- break;
- case RV_YEAR_3:
- year = (year * 10) + (ch - '0');
- switch (year >= 1600 && year <= 2399) { //checking
- case 1:
- state = RV_VALIDDATE;
- break;
- case 0:
- default:
- state = RV_INVALIDDATE;
- break;
- }
- break;
- case RV_NODATE:
- break;
- case RV_VALIDDATE:
- switch (acceptChar) {
- case 1:
- break;
- case 0:
- default:
- state = RV_NODATE;
- }
- break;
- case RV_DAY_2:
- case RV_MONTH_2:
- case RV_INVALIDDATE:
- state = RV_NODATE;
- break;
- default:
- state = RV_INVALIDDATE;
- break;
- }
- break;
- case 0:
- switch(state) {
- case RV_NODATE:
- break;
- case RV_INVALIDDATE:
- break;
- case RV_YEAR_2:
- case RV_VALIDDATE:
- switch (isblank(ch)) {
- case 1:
- state = RV_VALIDDATE;
- acceptChar = 1;
- break;
- case 0:
- switch (acceptChar) {
- case 1:
- break;
- case 0:
- default:
- state = RV_NODATE;
- break;
- }
- break;
- default:
- state = RV_NODATE;
- break;
- }
- break;
- default:
- switch(ch){
- case '/':
- switch(canAcceptDash || expectingDash) {
- case 1:
- switch (dateState) {
- case MONTH_STATE:
- state = RV_DAY_0;
- expectingDash = 0;
- canAcceptDash = 0;
- break;
- case DAY_STATE:
- state = RV_YEAR_0;
- expectingDash = 0;
- canAcceptDash = 0;
- break;
- }
- break;
- case 0:
- default:
- state = RV_NODATE;
- break;
- }
- break;
- default:
- switch (isblank(ch)) {
- case 1:
- state = RV_START;
- break;
- default:
- state = RV_NODATE;
- break;
- }
- break;
- }
- break;
- }
- break;
- default:
- state = RV_NODATE;
- break;
- }
- ch = getchar();
- }
- switch (state) {
- case RV_START:
- case RV_MONTH_1:
- case RV_MONTH_2:
- case RV_DAY_0:
- case RV_DAY_1:
- case RV_DAY_2:
- case RV_YEAR_0:
- case RV_YEAR_1:
- case RV_YEAR_3:
- state = RV_NODATE;
- break;
- case RV_YEAR_2:
- state = RV_VALIDDATE;
- default:
- break;
- }
- switch (state) {
- case RV_VALIDDATE:
- switch (validate_date(month, day, year)) {
- case 1:
- state = RV_VALIDDATE;
- break;
- case 0:
- default:
- state = RV_INVALIDDATE;
- break;
- }
- break;
- default:
- break;
- }
- //printf("month: %d day: %d year: %d \n", month, day, year);
- return state;
- }
- /***** main *****/
- /* Do not change the main function. */
- int main(void)
- {
- // run the loop until hit end of file
- do {
- int rv = get_date();
- if (!feof(stdin)) {
- switch (rv) {
- case RV_NODATE:
- printf("No date found.\n");
- break;
- case RV_VALIDDATE:
- printf("Valid date.\n");
- break;
- case RV_INVALIDDATE:
- printf("Invalid date.\n");
- break;
- default:
- printf("Unknown return value %d.\n", rv);
- break;
- }
- }
- } while (! feof(stdin));
- return 0;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement