I'm developing an application about bank holidays in many countries.
To find bank holidays dates in China I need to convert dates to Chinese system.
I have found many libraries in different languages, like :
this one : https://github.com/v5developer/maven-framework-project/blob/master/aimeizi-tutorials/src/main/java/net/aimeizi/tutorials/LunarCalendar.java that I transposed to Apex language
this one https://www.javascriptbank.com/javascript/time/Lunar_Calendar_script/amlich-hnd.js in js (it's for Vietnam but seems to work about the same)
or this one https://github.com/magiclen/JavaChineseCalendar/blob/master/src/main/java/org/magiclen/%E8%BE%B2%E6%9B%86/%E8%BE%B2%E6%9B%86.java
and more.
All of them use an array of numbers, with one number per year, like this one :
final static long[] lunarInfo = new long[] { 0x04bd8, 0x04ae0, 0x0a570,
0x054d5, 0x0d260, 0x0d950, 0x16554, 0x056a0, 0x09ad0, 0x055d2,
0x04ae0, 0x0a5b6, 0x0a4d0, 0x0d250, 0x1d255, 0x0b540, 0x0d6a0,
0x0ada2, 0x095b0, 0x14977, 0x04970, 0x0a4b0, 0x0b4b5, 0x06a50,
0x06d40, 0x1ab54, 0x02b60, 0x09570, 0x052f2, 0x04970, 0x06566,
0x0d4a0, 0x0ea50, 0x06e95, 0x05ad0, 0x02b60, 0x186e3, 0x092e0,
0x1c8d7, 0x0c950, 0x0d4a0, 0x1d8a6, 0x0b550, 0x056a0, 0x1a5b4,
0x025d0, 0x092d0, 0x0d2b2, 0x0a950, 0x0b557, 0x06ca0, 0x0b550,
0x15355, 0x04da0, 0x0a5d0, 0x14573, 0x052d0, 0x0a9a8, 0x0e950,
0x06aa0, 0x0aea6, 0x0ab50, 0x04b60, 0x0aae4, 0x0a570, 0x05260,
0x0f263, 0x0d950, 0x05b57, 0x056a0, 0x096d0, 0x04dd5, 0x04ad0,
0x0a4d0, 0x0d4d4, 0x0d250, 0x0d558, 0x0b540, 0x0b5a0, 0x195a6,
0x095b0, 0x049b0, 0x0a974, 0x0a4b0, 0x0b27a, 0x06a50, 0x06d40,
0x0af46, 0x0ab60, 0x09570, 0x04af5, 0x04970, 0x064b0, 0x074a3,
0x0ea50, 0x06b58, 0x055c0, 0x0ab60, 0x096d5, 0x092e0, 0x0c960,
0x0d954, 0x0d4a0, 0x0da50, 0x07552, 0x056a0, 0x0abb7, 0x025d0,
0x092d0, 0x0cab5, 0x0a950, 0x0b4a0, 0x0baa4, 0x0ad50, 0x055d9,
0x04ba0, 0x0a5b0, 0x15176, 0x052b0, 0x0a930, 0x07954, 0x06aa0,
0x0ad50, 0x05b52, 0x04b60, 0x0a6e6, 0x0a4e0, 0x0d260, 0x0ea65,
0x0d530, 0x05aa0, 0x076a3, 0x096d0, 0x04bd7, 0x04ad0, 0x0a4d0,
0x1d0b6, 0x0d250, 0x0d520, 0x0dd45, 0x0b5a0, 0x056d0, 0x055b2,
0x049b0, 0x0a577, 0x0a4b0, 0x0aa50, 0x1b255, 0x06d20, 0x0ada0 };
used to calculate various numbers, like in
final private static int yearDays(int y) {
int i, sum = 348;
for (i = 0x8000; i > 0x8; i >>= 1) {
if ((lunarInfo[y - 1900] & i) != 0)
sum += 1;
}
return (sum + leapDays(y));
}
final private static int leapDays(int y) {
if (leapMonth(y) != 0) {
if ((lunarInfo[y - 1900] & 0x10000) != 0)
return 30;
else
return 29;
} else
return 0;
}
I've been searching in libraries comments, documentations, gerneral info about China, and I learnt a lot about the chinese calendar but couldn't find what these numbers are.... and where they come from.
It doesn't prevent me from using it but I like to understand what I code... Any explanations ?
Thanks
I finally came to understand that, at least for this code https://github.com/v5developer/maven-framework-project/blob/master/aimeizi-tutorials/src/main/java/net/aimeizi/tutorials/LunarCalendar.java, it's just a way to store data :
The data is encoded on 17 bits with :
bit 17 : number of days in leap month , 1=>30, 0=>29
bits 16 to 5 : number of days in each month, 0=>29, 1=>30
bits 4 to 1 : number of the leap month in the year in binary.
So 0x16554 (7th in the list, so year 1906) is 10110010101010100 in binary with a 17 bits length, which means :
10110010101010100 : There is a leap month, it's month 4
10110010101010100 : The leap month has 30 days
10110010101010100 : The 1st month has 29 days
10110010101010100 : The 2nd month has 30 days
...
10110010101010100 : The 12th month has 30 days
which can be checked here : https://www.asia-home.com//china/calendrier-chinois/year/1906.php
In other codes the meaning can vary but the idea is the same.
I want to make a simple program to count debt installments. The requirements are:
Input the debt value
Input how long the installments
The first half of the installment bank interest is 11% and the rest are 8%
Must use maps
Here's my code
package main
import "fmt"
func main() {
fmt.Print("Input the debt value : ")
var debt int
fmt.Scanln(&debt)
fmt.Print("Input how long the installments : ")
var installment int
fmt.Scanln(&installment)
fmt.Println("====================================================")
fmt.Println("Total debt : ", debt)
fmt.Println("Installments : ", installment)
fmt.Println("====================================================")
var firstHalf = installment / 2
var pay int
for i := 1; i <= installment; i++ {
value := map[string]int{
"month": i,
"payment": pay,
}
if i <= firstHalf {
pay = (debt / installment) + (debt * 11 / 100)
fmt.Println(value["month"],"Installment with bank interest (11%) is", value["payment"])
} else {
pay = (debt / installment) + (debt * 8 / 100)
fmt.Println(value["month"],"Installment with bank interest (8%) is", value["payment"])
}
}
}
If I run the code and for example :
The debt is 10.000.000
The installments are 7 months
Here's the output :
1 Installment with bank interest (11%) is 0
2 Installment with bank interest (11%) is 2528571
3 Installment with bank interest (11%) is 2528571
4 Installment with bank interest (8%) is 2528571
5 Installment with bank interest (8%) is 2228571
6 Installment with bank interest (8%) is 2228571
7 Installment with bank interest (8%) is 2228571
I don't know why the first index is always 0, even the next calculation is right. So, I guess that either I am using the wrong syntax or I am trying to do something that can not be done. Maybe most likely experienced people will see right away what is wrong.
if i <= firstHalf {
pay = (debt / installment) + (debt * 11 / 100)
value["payment"] = pay
fmt.Println(value["month"],"Installment with bank interest (11%) is",
value["payment"])
} else {
pay = (debt / installment) + (debt * 8 / 100)
value["payment"] = pay
fmt.Println(value["month"],"Installment with bank interest (8%) is",
value["payment"])
}
It is printing the the payment value of map as 0 because it is assigned with pay which has no value initially.You can fix this by declaring the map beneath the if else condition and then print your values,here is the modified code for the same logic:
package main
import "fmt"
func main() {
fmt.Print("Input the debt value : ")
var debt int
fmt.Scanln(&debt)
fmt.Print("Input how long the installments : ")
var installment int
fmt.Scanln(&installment)
fmt.Println("====================================================")
fmt.Println("Total debt : ", debt)
fmt.Println("Installments : ", installment)
fmt.Println("====================================================")
var firstHalf = installment / 2
var pay int
for i := 1; i <= installment; i++ {
if i <= firstHalf {
pay = (debt / installment) + (debt * 11 / 100)
} else {
pay = (debt / installment) + (debt * 8 / 100)
}
value := map[string]int{
"month": i,
"payment": pay,
}
if i <= firstHalf {
fmt.Println(value["month"], "Installment with bank interest (11%) is", value["payment"])
} else {
fmt.Println(value["month"], "Installment with bank interest (8%) is", value["payment"])
}
}
}
Output:
Input the debt value : 1000
Input how long the installments : 5
====================================================
Total debt : 1000
Installments : 5
====================================================
1 Installment with bank interest (11%) is 310
2 Installment with bank interest (11%) is 310
3 Installment with bank interest (8%) is 280
4 Installment with bank interest (8%) is 280
5 Installment with bank interest (8%) is 280
Beginner here. I just wanted to know how and where I went wrong with this code. I’m having problem with using the modulo for the time. The following is the problem and the code I created.
A company wants to create a system that automatically computes for the total fee of the parking services in their new mall.
The user first needs to input their vehicle type, time-in and time-out. Then, it will compute for the total fee of the parking service based on the time the vehicle spent parked. Use the table below as basis:
Vehicle Type First 3 hours After 3 hours
M-otorcycle FREE PHP 10.00/hr
C-ar PHP 30.00 PHP 10.00/hr
T-ruck PHP 50.00 PHP 25.00/hr
Assumptions:
User will not input a value wherein Timeout < Timein.
Max Inputs will for time will be from 0000 to 2359, and it will always follow that form (user will not input values like 13, 17, 110).
Input Format
Vehicle Type, Time-in, and Time-out
Input Sample
M
1230
1430
Output Format
Payment, hours and minutes in this format.
Output Sample
Payment:·0.00
Hours:·2
Minutes:·0
Code:
#include<stdio.h>
int main()
{
double payment;
int time, entry,exit;
int hours, minutes;
char type;
scanf("%c %d %d", &type, &entry, &exit);
hours = (exit-entry)/100;
minutes = (exit-entry) %60;
if (type == 'M' && time > 3)
payment = hours*10;
else
payment = hours*0;
if (type=='C' && time >= 3)
payment = ((hours-3)*10)+30;
else
payment = 30;
if (type == 'T' && hours >= 3)
payment = ((hours-3)*25)+50;
else
payment = 50;
printf("Payment: %.2f \nHours: %d \nMinutes: %d ", payment, hours, minutes);
return 0;
}
Can u send the table clearly.
And also,
minutes = abs((exit/100) - (entry/100));
No use of modulus!
As a little background: in October 1582 the Gregorian calendar was introduced to correct problems with the Julian calendar, which was in use until then. The Gregorian calendar specifies the length of a year more precisely, adds a new leap year calculation and removes 10 days from the Julian calendar on transition (moving from 4.Oct.1582 to 15.Oct.1582)
// Julian leap year calculation
((year % 4) == 0)
// Gregorian leap year calculation
((year % 4) == 0 && (year % 100) != 0) || (year % 400) == 0)
To sum up all calendar days from 1 AD to 2001 AD I use:
#include <stdio.h>
int main( void)
{
int year;
int daysInYear;
int total;
total = 0;
for( year = 1; year <= 2001; year++)
{
//
daysInYear = 365;
if( year < 1582)
daysInYear += ((year % 4) == 0);
else
if( year > 1582)
daysInYear += ((year % 4) == 0 && (year % 100) != 0) || ((year % 400) == 0);
else
daysInYear -= 10; // 1582 exactly
total += daysInYear;
printf( "%d: +%d = %d\n", year, daysInYear, total);
}
return( 0);
}
Now running this exhaustively over all years from 1 to 2000 gives this pastebin: https://pastebin.com/bR7hwNr1
The most interesting bits show that the leap year and day-skip calculation is correct and also produces the result:
1: +365 = 365
2: +365 = 730
3: +365 = 1095
4: +366 = 1461
...
100: +366 = 36525
...
400: +366 = 146100
...
1581: +365 = 577460
1582: +355 = 577815
1583: +365 = 578180
...
1900: +365 = 693962
...
1996: +366 = 729026
1997: +365 = 729391
1998: +365 = 729756
1999: +365 = 730121
2000: +366 = 730487
Now the question is this: the 1.1.2001 is at 730487 elapsed calendar days. Given the length of the year as defined by the Gregorian calendar as 365.2425, I would expect to see 2000*365.2425 = 730485 days. If one uses tropical days or solar days it would be 730484. But 740487 is clearly out of range.
Assuming that no-one miscounted any days in the Gregorian Calendar range, there are some extra days in the Julian Calendar, that don't match with the tropical days. But the Gregorian was created to correct the Julian calendar and I don't think they would have made that large an error in 1582.
This could be more a historical question than a programming question I would guess.
The goal of the Gregorian reform of the calendar was to reset the date of the northern hemisphere vernal equinox to March 21, and keep it there. This date was chosen because that was the approximate average date of the equinox at the time of the Council of Nicaea in AD 325. At the time of the council, the date of the equinox had slipped from about March 25 in AD 1.
For all the details read the book Gregorian Reform of the Calendar which is the proceedings of a conference held by the Vatican Observatory and published in 1983.
To clarify, when evaluating the Gregorian calendar compared to the Julian, using a mix of Julian and Gregorian dates incorporates the one-time correction of 10 days which was intended to correct for accumulated excess leap years from about AD 325 to AD 1582. If one wishes to use some start date other than AD 325, the entire calculation should use ONLY Gregorian dates or ONLY Julian dates.
The prompt is:
Implement a function that reads in a string containing a textual description of a cal- endar date and that prints out the corresponding day of the week (Monday–Sunday). The two valid input formats for this function are:
mm/dd/yyyy
Example: 03/04/2014
Output: Tuesday
Month dd, yyyy
Example: March 04, 2014
Output: Tuesday
where dd is the numeric day, mm is the numeric month, yyyy is the year and Month is the name of the month. All days and months are specified using two digits (i.e. for March, use 03 instead of 3). In the second valid format, there is a single space between Month and dd and between dd, and yyyy.
In order to receive full credit on this task, your program should print out the correct day of the week for any input in a correct format.
So as of right now i am able to get the correct days for every single day except in the years 2005 2009 2013 2017 etc etc... they are always a day behind, i notice that its going by a trend of every 4 years the days end up 1 day behind. Im not sure whats wrong. is it cause my method of using 365.25 as each year is wrong?
My code:
#include<stdio.h>
int main()
{
int month,day1,day2,totdays,year,dm,dn,leap,rmd;
printf(" ");
scanf("%d/%d/%d",&month,&day1,&year);
if(((year%4==0) && (year%100!=0)) || (year%400==0))
{
if(month==1)
dm=0;
if(month==2)
dm=31;
if(month==3)
dm=60;
if(month==4)
dm=91;
if(month==5)
dm=121;
if(month==6)
dm=152;
if(month==7)
dm=182;
if(month==8)
dm=213;
if(month==9)
dm=244;
if(month==10)
dm=274;
if(month==11)
dm=305;
if(month==12)
dm=335;
}
else
{
if(month==1)
dm=0;
if(month==2)
dm=31;
if(month==3)
dm=59;
if(month==4)
dm=90;
if(month==5)
dm=120;
if(month==6)
dm=151;
if(month==7)
dm=181;
if(month==8)
dm=212;
if(month==9)
dm=243;
if(month==10)
dm=273;
if(month==11)
dm=304;
if(month==12)
dm=334;
}
day2=(year-1970)*(365.25);
dn=dm+day1;
totdays=day2+dn;
rmd=totdays%7;
if(rmd==5)
{
printf("Monday \n");
}
if(rmd==6)
{
printf("Tuesday \n");
}
if(rmd==0)
{
printf("Wednesday \n");
}
if(rmd==1)
{
printf("Thursday \n");
}
if(rmd==2)
{
printf("Friday \n");
}
if(rmd==3)
{
printf("Saturday \n");
}
if(rmd==4)
{
printf("Sunday \n");
}
return 0;
}
1969 wasn't a leap year, 1972 was. When you do
day2=(year-1970)*(365.25);
to discover how many days off January 1st of year year is, you'll count
0 days for '70
365.25 days for '71
730.5 days for '72
1095.75 days for '73
1461 days for '74
The fractional portion of the floating point calculation is truncated, so day2 isn't going to count the extra day from 02/29/1972 until 01/01/1974, instead of 01/01/1973 as it should.
Put another way, you are making the assumption that 1970 was the first year after a leap year, so a leap day won't be counted until four years later.
The day2 calculation won't work. There are 1461 days in every four year period. First you need to compute how many 4 year periods have passed. Then figure out how many days there were to the beginning of the specified year, similar to what you did for the months.
The year%100 and year%400 exceptions add a little complexity, but fortunately the year 2000 was a leap year, so the first time you have to deal with that little wrinkle is the year 2100.