How to calculate the Easter date in PL/SQL Oracle Headquarters Redwood Shores1 e1698667100526

How to calculate the Easter date in PL/SQL

Ever wondered how they Easter date is determined? And, even more important, how it is to be maintained in you application. Manually updating the date every year is an option, but it’s always better to calculate it on the fly. It’s not easy because it depends on the age of the moon at january 1st and uses the moonyear cycle.

So, here’s some pl/sql which calculates Easter sunday for any given year:

create or replace function bepaal_paasdatum( p_jaar in number default to_numbeR(to_char( sysdate, ‘yyyy’) )) return date is
VolleMaan    Date;
GuldenGetal  pls_Integer;
SchrikkelDg  pls_Integer := 14;
Epacta       pls_Integer;
KritEpacta   pls_Integer;
begin
/* first we calculate the “golden number” of the year; we divide the year with the years in a moonyear cycle (19), and add 1
(see http://en.wikipedia.org/wiki/Golden_numbers)
*/
Guldengetal := mod( p_jaar, 19 ) +1;
/*
epacta is the age of the moon at januari 1st
*/
Epacta      := mod((GuldenGetal * 11 )- SchrikkelDg + 2, 30);
/*
calculate the full moons in a year
*/
VolleMaan   := to_Date(’13-03-‘||to_char( p_jaar), ‘dd-mm-yyyy’ ) + 31 – Epacta;
If (mod( p_jaar , 4) = 0 and mod(p_jaar, 100) != 0 ) or mod(p_jaar, 400) = 0
Then
VolleMaan := VolleMaan – 1;
end if;

If VolleMaan < to_Date(’22-03-‘||to_char( p_jaar), ‘dd-mm-yyyy’ )
Then
If GuldenGetal > 11
Then
KritEpacta := 26;
Else
KritEpacta := 25;
End If;

If Epacta < KritEpacta
Then
VolleMaan := VolleMaan + 29;
Else
VolleMaan := VolleMaan + 30;
End If;
End If;
vollemaan := vollemaan +1 ;
while to_char(vollemaan, ‘d’) != 1 –zondag zoeken
loop
vollemaan := vollemaan + 1;
end loop;

return( VolleMaan   );
end;
/

The results:

PATRICK> begin
2   for i in 1990 .. 2010
3  loop
4  dbms_output.put_line( ‘jaar ‘||i||’; ‘|| bepaal_paasdatum(i));
5  end loop;
6  end;
7  /
jaar 1990; 15-APR-90
jaar 1991; 31-MAR-91
jaar 1992; 19-APR-92
jaar 1993; 11-APR-93
jaar 1994; 03-APR-94
jaar 1995; 16-APR-95
jaar 1996; 07-APR-96
jaar 1997; 30-MAR-97
jaar 1998; 12-APR-98
jaar 1999; 04-APR-99
jaar 2000; 23-APR-00
jaar 2001; 15-APR-01
jaar 2002; 31-MAR-02
jaar 2003; 20-APR-03
jaar 2004; 11-APR-04
jaar 2005; 27-MAR-05
jaar 2006; 16-APR-06
jaar 2007; 08-APR-07
jaar 2008; 20-APR-08
jaar 2009; 12-APR-09
jaar 2010; 04-APR-10

PL/SQL procedure successfully completed.

PATRICK>

I’ve checked the dates against easter dates found on internet, and it seems right. Except…. the date for next year! Sources on internet mention March 23th, 2008, but my function returns April 20th.

I hate to say I have no clue where the problem is. So, if you plan to use my function you’ll either should find the bug or implement it after 2008! Some people suggested I have a real Easter Egg in my code….

6 Comments

  1. fortius December 1, 2010
  2. Anton Scheffer June 25, 2007
  3. Anton Scheffer June 25, 2007
  4. Patrick Sinke June 22, 2007
  5. Howard Rogers June 22, 2007
  6. p3t0r June 22, 2007