日历的各种C语言实现方法

日历的各种C语言实现方法

方法一:基础版日历(指定年月)

cpp 复制代码
#include <stdio.h>

// 判断是否为闰年
int isLeapYear(int year) {
    return (year % 4 == 0 && year % 100 != 0) || (year % 400 == 0);
}

// 获取某年某月的天数
int getDaysInMonth(int year, int month) {
    int days[] = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
    if (month == 2 && isLeapYear(year)) {
        return 29;
    }
    return days[month - 1];
}

// 计算某年某月1日是星期几 (0=周日, 1=周一, ..., 6=周六)
int getFirstDayOfWeek(int year, int month) {
    int day = 1;
    // 使用Zeller公式
    if (month < 3) {
        month += 12;
        year--;
    }
    int k = year % 100;
    int j = year / 100;
    int h = (day + 13*(month + 1)/5 + k + k/4 + j/4 + 5*j) % 7;
    return (h + 6) % 7; // 转换为0=周日, 1=周一, ..., 6=周六
}

// 打印日历
void printCalendar(int year, int month) {
    printf("\n     %d年%d月\n", year, month);
    printf("日 一 二 三 四 五 六\n");
    
    int firstDay = getFirstDayOfWeek(year, month);
    int daysInMonth = getDaysInMonth(year, month);
    
    // 打印前面的空格
    for (int i = 0; i < firstDay; i++) {
        printf("   ");
    }
    
    // 打印日期
    for (int day = 1; day <= daysInMonth; day++) {
        printf("%2d ", day);
        if ((day + firstDay) % 7 == 0) {
            printf("\n");
        }
    }
    printf("\n");
}

int main() {
    int year, month;
    
    printf("请输入年份: ");
    scanf("%d", &year);
    printf("请输入月份: ");
    scanf("%d", &month);
    
    if (month < 1 || month > 12) {
        printf("月份输入错误!\n");
        return 1;
    }
    
    printCalendar(year, month);
    return 0;
} 

方法二:全年日历显示

cpp 复制代码
 #include <stdio.h>

int isLeapYear(int year) {
    return (year % 4 == 0 && year % 100 != 0) || (year % 400 == 0);
}

int getDaysInMonth(int year, int month) {
    int days[] = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
    if (month == 2 && isLeapYear(year)) {
        return 29;
    }
    return days[month - 1];
}

int getFirstDayOfWeek(int year, int month) {
    int day = 1;
    if (month < 3) {
        month += 12;
        year--;
    }
    int k = year % 100;
    int j = year / 100;
    int h = (day + 13*(month + 1)/5 + k + k/4 + j/4 + 5*j) % 7;
    return (h + 6) % 7;
}

void printMonthCalendar(int year, int month) {
    char *monthNames[] = {"一月", "二月", "三月", "四月", "五月", "六月",
                         "七月", "八月", "九月", "十月", "十一月", "十二月"};
    
    printf("\n     %s %d\n", monthNames[month-1], year);
    printf("日 一 二 三 四 五 六\n");
    
    int firstDay = getFirstDayOfWeek(year, month);
    int daysInMonth = getDaysInMonth(year, month);
    
    for (int i = 0; i < firstDay; i++) {
        printf("   ");
    }
    
    for (int day = 1; day <= daysInMonth; day++) {
        printf("%2d ", day);
        if ((day + firstDay) % 7 == 0) {
            printf("\n");
        }
    }
    printf("\n");
}

void printYearCalendar(int year) {
    printf("\n========== %d年日历 ==========\n", year);
    
    for (int month = 1; month <= 12; month++) {
        printMonthCalendar(year, month);
        if (month % 3 == 0) {
            printf("\n");
        }
    }
}

int main() {
    int year;
    
    printf("请输入年份: ");
    scanf("%d", &year);
    
    printYearCalendar(year);
    return 0;
}

方法三:季度日历显示

cpp 复制代码
#include <stdio.h>

int isLeapYear(int year) {
    return (year % 4 == 0 && year % 100 != 0) || (year % 400 == 0);
}

int getDaysInMonth(int year, int month) {
    int days[] = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
    if (month == 2 && isLeapYear(year)) {
        return 29;
    }
    return days[month - 1];
}

int getFirstDayOfWeek(int year, int month) {
    int day = 1;
    if (month < 3) {
        month += 12;
        year--;
    }
    int k = year % 100;
    int j = year / 100;
    int h = (day + 13*(month + 1)/5 + k + k/4 + j/4 + 5*j) % 7;
    return (h + 6) % 7;
}

void printQuarterCalendar(int year, int quarter) {
    char *monthNames[] = {"一月", "二月", "三月", "四月", "五月", "六月",
                         "七月", "八月", "九月", "十月", "十一月", "十二月"};
    
    printf("\n========== %d年第%d季度 ==========\n", year, quarter);
    
    int startMonth = (quarter - 1) * 3 + 1;
    int endMonth = startMonth + 2;
    
    for (int month = startMonth; month <= endMonth; month++) {
        printf("\n     %s %d\n", monthNames[month-1], year);
        printf("日 一 二 三 四 五 六\n");
        
        int firstDay = getFirstDayOfWeek(year, month);
        int daysInMonth = getDaysInMonth(year, month);
        
        for (int i = 0; i < firstDay; i++) {
            printf("   ");
        }
        
        for (int day = 1; day <= daysInMonth; day++) {
            printf("%2d ", day);
            if ((day + firstDay) % 7 == 0) {
                printf("\n");
            }
        }
        printf("\n");
    }
}

int main() {
    int year, quarter;
    
    printf("请输入年份: ");
    scanf("%d", &year);
    printf("请输入季度(1-4): ");
    scanf("%d", &quarter);
    
    if (quarter < 1 || quarter > 4) {
        printf("季度输入错误!\n");
        return 1;
    }
    
    printQuarterCalendar(year, quarter);
    return 0;
}

方法四:带当前日期标记的日历

cpp 复制代码
 #include <stdio.h>
#include <time.h>

int isLeapYear(int year) {
    return (year % 4 == 0 && year % 100 != 0) || (year % 400 == 0);
}

int getDaysInMonth(int year, int month) {
    int days[] = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
    if (month == 2 && isLeapYear(year)) {
        return 29;
    }
    return days[month - 1];
}

int getFirstDayOfWeek(int year, int month) {
    int day = 1;
    if (month < 3) {
        month += 12;
        year--;
    }
    int k = year % 100;
    int j = year / 100;
    int h = (day + 13*(month + 1)/5 + k + k/4 + j/4 + 5*j) % 7;
    return (h + 6) % 7;
}

void printCalendarWithToday(int year, int month) {
    // 获取当前日期
    time_t t = time(NULL);
    struct tm *today = localtime(&t);
    int current_year = today->tm_year + 1900;
    int current_month = today->tm_mon + 1;
    int current_day = today->tm_mday;
    
    printf("\n     %d年%d月", year, month);
    if (year == current_year && month == current_month) {
        printf(" (当前月份)");
    }
    printf("\n");
    
    printf("日 一 二 三 四 五 六\n");
    
    int firstDay = getFirstDayOfWeek(year, month);
    int daysInMonth = getDaysInMonth(year, month);
    
    for (int i = 0; i < firstDay; i++) {
        printf("   ");
    }
    
    for (int day = 1; day <= daysInMonth; day++) {
        // 标记当前日期
        if (year == current_year && month == current_month && day == current_day) {
            printf("[%2d]", day); // 用方括号标记今天
        } else {
            printf("%2d ", day);
        }
        
        if ((day + firstDay) % 7 == 0) {
            printf("\n");
        }
    }
    printf("\n");
}

int main() {
    int year, month;
    
    printf("请输入年份: ");
    scanf("%d", &year);
    printf("请输入月份: ");
    scanf("%d", &month);
    
    if (month < 1 || month > 12) {
        printf("月份输入错误!\n");
        return 1;
    }
    
    printCalendarWithToday(year, month);
    return 0;
}

方法五:命令行交互式日历

cpp 复制代码
 #include <stdio.h>
#include <stdlib.h>

int isLeapYear(int year) {
    return (year % 4 == 0 && year % 100 != 0) || (year % 400 == 0);
}

int getDaysInMonth(int year, int month) {
    int days[] = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
    if (month == 2 && isLeapYear(year)) {
        return 29;
    }
    return days[month - 1];
}

int getFirstDayOfWeek(int year, int month) {
    int day = 1;
    if (month < 3) {
        month += 12;
        year--;
    }
    int k = year % 100;
    int j = year / 100;
    int h = (day + 13*(month + 1)/5 + k + k/4 + j/4 + 5*j) % 7;
    return (h + 6) % 7;
}

void printCalendar(int year, int month) {
    char *monthNames[] = {"一月", "二月", "三月", "四月", "五月", "六月",
                         "七月", "八月", "九月", "十月", "十一月", "十二月"};
    
    printf("\n┌─────────────────────┐\n");
    printf("│     %s %d     │\n", monthNames[month-1], year);
    printf("├─────────────────────┤\n");
    printf("│日 一 二 三 四 五 六 │\n");
    printf("├─────────────────────┤\n");
    
    int firstDay = getFirstDayOfWeek(year, month);
    int daysInMonth = getDaysInMonth(year, month);
    
    printf("│");
    for (int i = 0; i < firstDay; i++) {
        printf("   ");
    }
    
    for (int day = 1; day <= daysInMonth; day++) {
        printf("%2d ", day);
        if ((day + firstDay) % 7 == 0 && day != daysInMonth) {
            printf("│\n│");
        }
    }
    
    // 填充剩余空格
    int remaining = (7 - (daysInMonth + firstDay) % 7) % 7;
    for (int i = 0; i < remaining; i++) {
        printf("   ");
    }
    printf("│\n");
    printf("└─────────────────────┘\n");
}

void showMenu() {
    printf("\n========== 日历系统 ==========\n");
    printf("1. 查看指定年月日历\n");
    printf("2. 查看全年日历\n");
    printf("3. 查看当前月份\n");
    printf("4. 退出\n");
    printf("请选择操作: ");
}

int main() {
    int choice;
    int year, month;
    
    while (1) {
        showMenu();
        scanf("%d", &choice);
        
        switch (choice) {
            case 1:
                printf("请输入年份: ");
                scanf("%d", &year);
                printf("请输入月份: ");
                scanf("%d", &month);
                if (month >= 1 && month <= 12) {
                    printCalendar(year, month);
                } else {
                    printf("月份输入错误!\n");
                }
                break;
                
            case 2:
                printf("请输入年份: ");
                scanf("%d", &year);
                for (month = 1; month <= 12; month++) {
                    printCalendar(year, month);
                }
                break;
                
            case 3:
                {
                    time_t t = time(NULL);
                    struct tm *now = localtime(&t);
                    year = now->tm_year + 1900;
                    month = now->tm_mon + 1;
                    printCalendar(year, month);
                }
                break;
                
            case 4:
                printf("感谢使用日历系统!\n");
                exit(0);
                
            default:
                printf("无效选择,请重新输入!\n");
        }
    }
    
    return 0;
}

各版本特点总结

  1. 基础版:最简单的实现,适合初学者理解日历算法

  2. 全年版:显示整年日历,便于查看全年日期分布

  3. 季度版:按季度显示,适合商业和学术用途

  4. 标记版:突出显示当前日期,实用性更强

  5. 交互版:完整的命令行程序,提供友好的用户界面

核心技术点

  1. 闰年判断:使用标准的闰年判断规则

  2. Zeller公式:计算某天是星期几的经典算法

  3. 日期对齐:正确处理每月1日的星期位置

  4. 用户交互:提供多种查看方式和友好的界面

相关推荐
网安_秋刀鱼几秒前
【java安全】shiro鉴权绕过
java·开发语言·安全
k***92161 分钟前
【Linux】进程概念(六):地址空间核心机制
linux·运维·算法
【ql君】qlexcel3 分钟前
DDR学习笔记1
学习·ddr
xu_yule4 分钟前
算法基础-字符串哈希
算法·哈希算法·散列表
李白同学6 分钟前
Linux:调试器-gdb/cgdb使用
linux·服务器·c语言·c++
lixzest7 分钟前
C++中经常用的头文件介绍
数据结构·c++·算法
白昼流星!8 分钟前
C++内存四区与new操作符详解
开发语言·c++
tyatyatya8 分钟前
MATLAB三维绘图教程:plot3/mesh/surf/contour函数详解与实例
开发语言·matlab
十五年专注C++开发9 分钟前
标准C++操作文件方法总结
开发语言·c++·文件操作·ifstream
保持低旋律节奏12 分钟前
linux——进程调度(时间片+优先级轮转调度算法O(1))
linux·运维·算法