Traditional Culture Encyclopedia - Almanac inquiry - 5 1 lunar calendar

5 1 lunar calendar

Lunar calendar calculation method,

///Monthly data sheet

code uchar day _ code 1【9】= { 0x 0,0x 1f,0x3b,0x5a,0x78,0x97,0xb5,0xd4,0x F3 };

code uint day _ code 2【3】= { 0x 1 1 1,0x 130,0x 14e };

/*

Function: input BCD solar calendar data and output BCD lunar calendar data (only 190 1-2099 is allowed).

Example of calling function: transformation (c _ sun, year _ sun, month _ sun, day _ sun)

For example, calculate the conversion (0, 0x4, 0x 10, 0x 16) on June 6, 2004;

C_sun, Year _ Sun, Month _ Sun and Day _ Sun are all BCD data, C _ Sun is the century mark, and c_sun=0 is 2 1.

Ji, c_sun= 1 yes19th century.

After calling this function, the original data remains unchanged. Read C _ moon, Year _ moon, Month _ moon and Day _ moon to get the BCD data of the lunar calendar.

*/

Bit c _ moon

Data uchar year _ month, month _ month, day _ month, week;

/* subfunction, which is used to read the big month or small month of the lunar calendar in the data table. Returns 1 if the month is large, and 0*/ if the month is small.

Bit get _ moon _ day(uchar month _ p, uint table_addr)

{

Uchar temperature;

Switch (month p)

{

Case1:{temp = year _ code [table _ addr]&; 0x08

If(temp = = 0) returns (0); Else returns (1); }

Case 2: {temp = year _ code [table _ addr]&; 0x04

If(temp = = 0) returns (0); Else returns (1); }

Case 3: {temp = year _ code [table _ addr]&; 0x02

If(temp = = 0) returns (0); Else returns (1); }

Case 4: {temp = year _ code [table _ addr]&; 0x 0 1;

If(temp = = 0) returns (0); Else returns (1); }

Scenario 5: {temp = year _ code [table _ addr+1]&; 0x80

If(temp = = 0) returns (0); Else returns (1); }

Scenario 6: {temp = year _ code [table _ addr+1]&; 0x40

If(temp = = 0) returns (0); Else returns (1); }

Scenario 7: {temp = year _ code [table _ addr+1]&; 0x20

If(temp = = 0) returns (0); Else returns (1); }

Case 8: {temp = year _ code [table _ addr+1]&; 0x 10;

If(temp = = 0) returns (0); Else returns (1); }

Case 9: {temp = year _ code [table _ addr+1]&; 0x08

If(temp = = 0) returns (0); Else returns (1); }

Case10: {temp = year _ code [table _ addr+1]&; 0x04

If(temp = = 0) returns (0); Else returns (1); }

Case11:{temp = year _ code [table _ addr+1] & 0x02

If(temp = = 0) returns (0); Else returns (1); }

Case12: {temp = year _ code [table _ addr+1]&; 0x 0 1;

If(temp = = 0) returns (0); Else returns (1); }

Case13: {temp = year _ code [table _ addr+2]&; 0x80

If(temp = = 0) returns (0); Else returns (1); }

}

}

/*

Function: input BCD solar calendar data and output BCD lunar calendar data (only 190 1-2099 is allowed).

Example of calling function: transformation (c _ sun, year _ sun, month _ sun, day _ sun)

For example, calculate the conversion (0, 0x4, 0x 10, 0x 16) on June 6, 2004;

C_sun, Year _ Sun, Month _ Sun and Day _ Sun are all BCD data, C _ Sun is the century mark, and c_sun=0 is 2 1.

Ji, c_sun= 1 yes19th century.

After calling this function, the original data remains unchanged. Read C _ moon, Year _ moon, Month _ moon and Day _ moon to get the BCD data of the lunar calendar.

*/

Invalid conversion (C bit, Lunar Year, Lunar Month, Lunar Day)

{//c=0 is 2 1 century, and c= 1 yes19th century. All input and output data are BCD data.

uchar temp 1,temp2,temp3,month _ p;

uint temp4,table _ addr

Flag _ y; of bit flag2;

temp 1 = year/ 16; //BCD-& gt; Hex first converts the data into hexadecimal.

temp 2 = year % 16;

year = temp 1 * 10+temp 2;

Temp 1 = month/16;

temp 2 = month % 16;

month = temp 1 * 10+temp 2;

temp 1 = day/ 16;

temp 2 = day % 16;

day = temp 1 * 10+temp 2;

//Locate the data table address

If (c==0)

{

table _ addr =(year+0x 64- 1)* 0x 3;

}

other

{

table _ addr =(year- 1)* 0x 3;

}

//Data table address positioning is completed.

//Take the Gregorian calendar month in which the Spring Festival of that year is located.

temp 1 = year _ code【table _ addr+2】& amp; 0x60

temp 1 = _ cror _(temp 1,5);

//Take the Gregorian calendar month where the Spring Festival of that year is located.

//Subject to the Gregorian calendar day where the Spring Festival of that year is located.

temp 2 = year _ code【table _ addr+2】0x 1f;

//Subject to the Gregorian calendar day where the Spring Festival of that year is located.

//Calculate the number of days from spring to New Year's Day. The Spring Festival will only be held in 65438+ Gregorian calendar 10 or February.

if(temp 1 = = 0x 1)

{

temp 3 = temp 2- 1;

}

other

{

temp 3 = temp 2+0x 1f- 1;

}

//Calculate the number of days from spring to New Year's Day.

//In order to calculate the number of days from Gregorian calendar to New Year's Day, two tables are used to reduce the calculation.

//day _ code 1【9】,day _ code 2【3】

//If the Gregorian calendar month is before or before September, the number of days will be less than 0xff, and the table day _ code1[9] will be used.

//After September, if the number of days is greater than 0xff, use table day _ code2 [3].

//If the Gregorian calendar day is August 10, the number of days from Gregorian calendar day to New Year's Day is day _ code1[8-1]+10-1.

//If the Gregorian calendar day in 10 is10, the number of days from Gregorian calendar day to New Year's Day is day _ code2 [11-10]+10-/kloc.

If (month & lt 10)

{

temp 4 = day _ code 1【month- 1】+day- 1;

}

other

{

temp4 = day _ code 2【month- 10】+day- 1;

}

If ((month & gt0x2) amp& amp&(year %0x4==0))

{//If the Gregorian calendar month is greater than February and February of that year is a leap month, the number of days will increase by 1.

temp 4+= 1;

}

//Calculate the number of days from Gregorian calendar day to New Year's Day.

//Judge whether the Gregorian calendar day is before or after the Spring Festival.

if(temp 4 & gt; = temperature 3)

{//On the day after or on the day of Spring Festival in the solar calendar, use the following code to operate.

Temperature 4-= temperature 3;

month = 0x 1;

month _ p = 0x 1; //month_p refers to the month, and the calendar day is before the Spring Festival or month_p refers to the first month.

flag 2 = get _ moon _ day(month _ p,table _ addr);

//Check whether the lunar month is big or small. Returns 1 for large months and 0 for small months.

flag _ y = 0;

if(flag 2 = = 0)temp 1 = 0x 1d; //Abortion for 29 days

else temp 1 = 0x 1e; //Size 30 days

temp 2 = year _ code【table _ addr】& amp; 0xf0

temp 2 = _ cror _(temp 2,4); //Take the leap month of the year from the data table. If 0, there is no leap month in a year.

while(temp 4》gt; =temp 1)

{

temp 4-= temp 1;

month _ p+= 1;

if(month = = temp 2)

{

flag _ y = ~ flag _ y

If (flag_y==0)

Month+=1;

}

else month+= 1;

flag 2 = get _ moon _ day(month _ p,table _ addr);

if(flag 2 = = 0)temp 1 = 0x 1d;

else temp 1 = 0x 1e;

}

day = temp 4+ 1;

}

other

{//The day before the Spring Festival in the solar calendar, use the following code to operate.

Temperature 3-= temperature 4;

If (year ==0x0)

{

year = 0x63c = 1;

}

else year-= 1;

table _ addr-= 0x 3;

Month = 0xc

temp 2 = year _ code【table _ addr】& amp; 0xf0

temp 2 = _ cror _(temp 2,4);

If (temperature 2==0)

month _ p = 0xc

other

month _ p = 0xd//

/*month_p refers to the month. If there is a leap month in that year and there are thirteen months in a year, the month refers to 13, and there is no leap month to 12*/

flag _ y = 0;

flag 2 = get _ moon _ day(month _ p,table _ addr);

if(flag 2 = = 0)temp 1 = 0x 1d;

else temp 1 = 0x 1e;

while(temp 3 & gt; Temperature 1)

{

temp 3-= temp 1;

month _ p-= 1;

if(flag _ y = = 0)month-= 1;

if(month = = temp 2)flag _ y = ~ flag _ y;

flag 2 = get _ moon _ day(month _ p,table _ addr);

if(flag 2 = = 0)temp 1 = 0x 1d;

else temp 1 = 0x 1e;

}

day = temp 1-temp 3+ 1;

}

C _ moon = c// hexadecimal->; BCD, after operation, convert the data into BCD data.

temp 1 = year/ 10;

temp 1 = _ crol _(temp 1,4);

temp 2 = year % 10;

year _ moon = temp 1 | temp 2;

Temp 1 = month/10;

temp 1 = _ crol _(temp 1,4);

temp 2 = month % 10;

month _ moon = temp 1 | temp 2;

temp 1 = day/ 10;

temp 1 = _ crol _(temp 1,4);

temp 2 = day % 10;

day _ moon = temp 1 | temp 2;

}

/*************************************************************************

/* Function: input BCD solar calendar data and output BCD week data (only allowed 190 1-2099).

Example of calling function: conver _ week(c _ sun, year _ sun, month _ sun, day _ sun)

For example, calculate the conversion (0, 0x4, 0x 10, 0x 16) on June 6, 2004;

C_sun, Year _ Sun, Month _ Sun and Day _ Sun are all BCD data, C _ Sun is the century mark, and c_sun=0 is 2 1.

Ji, c_sun= 1 yes19th century.

After calling the function, the original data is unchanged, and the BCD data of the lunar calendar is obtained by reading the week.

*/

code uchar table _ week【 12】= { 0,3,3,6, 1,4,6,2,5,0,3,5 }; //Monthly correction data table

/*

Algorithm: the sum of date+year+leap years+positive number divided by 7 is the week, but if it is the week,

If the leap year is less than March, the sum above should be reduced by one day and divided by 7.

The number of weeks is 0

*/

Voidconver _ week (position c, lunar year, lunar month, lunar day)

{//c=0 is 2 1 century, and c= 1 yes19th century. All input and output data are BCD data.

uchar temp 1,temp2

temp 1 = year/ 16; //BCD-& gt; Hex first converts the data into hexadecimal.

temp 2 = year % 16;

year = temp 1 * 10+temp 2;

Temp 1 = month/16;

temp 2 = month % 16;

month = temp 1 * 10+temp 2;

temp 1 = day/ 16;

temp 2 = day % 16;

day = temp 1 * 10+temp 2;

if(c = = 0){ year+= 0x 64; }//If it is 2 1 century, add 100 to the number of years.

temp 1 = year/0x 4; //The number of leap years passed is only after 1900.

temp 2 = year+temp 1;

temp 2 = temp 2% 0x 7; //In order to save resources, make a remainder first, and avoid using integer data.

Temp 2 = temp 2+ day+table _ week [month-1];

If (year% 0x4 = = 0 & month & lt3) temp2-=1;

week = temp 2% 0x 7;

}