Code : Tout sélectionner
;Traduction du code ici http://mikhajduk.houa.org/EN/index.php?f=Links
;Translation from http://mikhajduk.houa.org/EN/index.php?f=Links
;{ Français
; Depuis l'ajustement du calendrier grégorien, sont bissextiles les années :
;
; soit divisibles par 4 mais non divisibles par 100 ;
; soit divisibles par 400.
;
; Donc, inversement, ne sont pas bissextiles les années :
;
; soit non divisibles par 4 ;
; soit divisibles par 100, mais pas par 400.
Procedure.l Bissextile(annee.l, option.l)
; DWORD IsLeapYear(DWORD année, DWORD option)
;
; Cette fonction détermine si une année est bissextile dans le calendrier choisi.
;
; Paramètres:
; annee - année,
; option - Calendrier (0 - Julien, 1 - Gregorien).
;
; Les valeurs retournées:
; * 1 si l'année est bissextile
; * 0 sinon,
; * -1 pour les paramètres non valides.
;
EnableASM
; PUSHFD
; PUSH ebx edx
checkparametres:
TEST option, -2 ; 0 <= Gregorian <= 1
JNZ l_bissextile_erreur
isynegative:
MOV eax, annee ; eax := Y =year
TEST eax, eax
JZ l_bissextile_erreur
JNS l_bissextile_quelcalendrier
; eax < 0 (Y < 0)
INC eax ; eax := eax + 1
NEG eax ; eax := -eax = -(Y + 1) = -Y - 1 =
; = |Y| - [Y < 0] = Y'
quelcalendrier:
CMP option, 0
JE l_bissextile_mod4
gregorien:
XOR edx, edx ; eax := E(eax / 100) = E(Y' / 100)
MOV ecx, 100 ; edx := eax mod 100 = Y' mod 100
DIV ecx ; div=(edx:eax)/ecx -> Quotient=eax Reste=edx
; Long .l 4 octets -2147483648 à +2 147 483 647
TEST edx, edx
JZ l_bissextile_mod4
MOV eax, edx ; eax := edx = Y' mod 100
;
; {(Y' mod 100) mod 4 = Y' mod 4}
mod4:
SHR eax, 1 ; eax := E(eax / 2); CF := eax mod 2
JC l_bissextile_resultat ;
SHR eax, 1 ; eax := E(eax / 2); CF := eax mod 2
JMP l_bissextile_resultat ;
erreur:
MOV eax, -1
JMP l_bissextile_fin
resultat:
SETNC al ; eax := not CF
MOVZX eax, al
fin:
; POP edx ebx
; POPFD
DisableASM
ProcedureReturn
EndProcedure
;}
;{ English
Procedure.l IsLeapYear(year.l, option.l)
; DWORD IsLeapYear(DWORD Y, DWORD Gregorian)
;
; This function determines if the given year is leap in the chosen calendar.
;
; Parameters:
; Y - year,
; Gregorian - chosen calendar (0 - Julian, 1 - Gregorian).
;
; Returned values:
; * 1 if the year Y is leap, 0 - in opposite case,
; * -1 for the invalid parameters.
;
EnableASM
; PUSHFD
; PUSH ebx edx
checkparameters:
TEST option, -2 ; 0 <= Gregorian <= 1
JNZ l_isleapyear_error
isynegative:
MOV eax, year ; eax := Y =year
TEST eax, eax
JZ l_isleapyear_error
JNS l_isleapyear_checkcalendar
; eax < 0 (Y < 0)
INC eax ; eax := eax + 1
NEG eax ; eax := -eax = -(Y + 1) = -Y - 1 =
; = |Y| - [Y < 0] = Y'
checkcalendar:
CMP option, 0
JE l_isleapyear_mod4
gregorian:
XOR edx, edx ; eax := E(eax / 100) = E(Y' / 100)
MOV ecx, 100 ; edx := eax mod 100 = Y' mod 100
DIV ecx ; div=(edx:eax)/ecx -> Quotient=eax Reste=edx
; Long .l 4 octets -2147483648 à +2 147 483 647
TEST edx, edx
JZ l_isleapyear_mod4
MOV eax, edx ; eax := edx = Y' mod 100
;
; {(Y' mod 100) mod 4 = Y' mod 4}
mod4:
SHR eax, 1 ; eax := E(eax / 2); CF := eax mod 2
JC l_isleapyear_result ;
SHR eax, 1 ; eax := E(eax / 2); CF := eax mod 2
JMP l_isleapyear_result ;
error:
MOV eax, -1
JMP l_isleapyear_theend
result:
SETNC al ; eax := not CF
MOVZX eax, al
theend:
; POP edx ebx
; POPFD
DisableASM
ProcedureReturn
EndProcedure
;}
Debug bissextile(2000,1)
Debug bissextile(2001,1)
Debug IsLeapYear(2000,1)
Debug IsLeapYear(2001,1)
; Macro from PAPIPP http://www.purebasic.fr/french/viewtopic.php?f=6&t=13296
; Macro _AN_BIS (x); cette macro définie si une année x est bissextile ou non
; ((Not((x%4)<>0)) & ((1-(Not((x%100)<>0)) ) | (Not(((x>>2)%100)<>0)) ) )
; EndMacro
; bissextile = 2016, 2008, 2000
; leap year = 2016, 2008, 2000