You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

新手求助:如何将DS3231的BCD日期数字转换为字符名称

嘿,我来帮你搞定这个问题!把数字形式的星期、月份转成对应名称其实超简单,用字符串数组映射的方法就能轻松实现,代码直观还容易理解,特别适合新手上手。

核心思路

我们可以提前把星期、月份的名称存在字符串数组里,等把DS3231返回的BCD数据转成十进制数字后,直接用数字作为索引(注意数组是从0开始的,所以要把数字减1),就能拿到对应的名称啦。

完整代码示例

先把你的代码补全并修改,实现需求:

#include "Wire.h"
#define rtcAddress 0x68
#include <BH1750_mega.h>
BH1750_mega LightSensor;

// 存储日期时间的变量
byte date_second, date_minute, date_hour, date_DOW, date_dayOfMonth, date_month, date_year;

// BCD转十进制的函数(补全你没写完的部分)
byte bin2dec(byte val) {
  // BCD格式是高4位存十位,低4位存个位,转成十进制就是高4位*10 + 低4位
  return ((val >> 4) * 10) + (val & 0x0F);
}

// 星期名称数组(对应DS3231返回的1-7,默认1=周日,需要调整顺序直接改数组就行)
const char* dayNames[] = {"周日", "周一", "周二", "周三", "周四", "周五", "周六"};
// 月份名称数组(对应1-12)
const char* monthNames[] = {"一月", "二月", "三月", "四月", "五月", "六月", 
                            "七月", "八月", "九月", "十月", "十一月", "十二月"};

void setup() {
  Wire.begin();
  Serial.begin(9600);
  LightSensor.begin();
}

void loop() {
  // 从DS3231读取7个字节的日期时间数据
  Wire.beginTransmission(rtcAddress);
  Wire.write(0); // 从第0个寄存器开始读
  Wire.endTransmission();
  Wire.requestFrom(rtcAddress, 7);

  // 读取并转成十进制
  date_second = bin2dec(Wire.read());
  date_minute = bin2dec(Wire.read());
  date_hour = bin2dec(Wire.read() & 0x3F); // 去掉24小时制的标志位,确保小时是0-23
  date_DOW = bin2dec(Wire.read());
  date_dayOfMonth = bin2dec(Wire.read());
  date_month = bin2dec(Wire.read() & 0x1F); // 去掉世纪标志位,确保月份是1-12
  date_year = bin2dec(Wire.read()) + 2000; // 加上2000,得到完整年份

  // 打印格式化后的日期(用数组映射名称)
  Serial.print("当前日期:");
  Serial.print(date_year);
  Serial.print("年");
  Serial.print(monthNames[date_month - 1]); // 数字减1对应数组索引
  Serial.print(date_dayOfMonth);
  Serial.print("日 ");
  Serial.println(dayNames[date_DOW - 1]); // 同理,数字减1拿对应星期名

  delay(1000); // 每秒更新一次
}

关键细节说明

  1. BCD转十进制:DS3231输出的是BCD编码(比如十进制15会存成0x15),bin2dec函数通过移位和位运算把它转成普通十进制数,方便后续使用。
  2. 数组索引对应:因为数组是从0开始计数的,而DS3231返回的星期是1-7、月份是1-12,所以要用数字-1来匹配数组的索引位置。
  3. 位掩码处理:读取小时和月份时加了& 0x3F、& 0x1F,是为了去掉寄存器里的额外标志位(比如小时的12/24制标识、月份的世纪标识),保证拿到的是正确的数字。
  4. 自定义调整:如果你的DS3231星期1对应的是周一而不是周日,只需要把dayNames数组的顺序改成{"周一", "周二", ..., "周日"}就行,灵活得很。

内容的提问来源于stack exchange,提问作者FitzVoid

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.21 04:09:31