Actions

Perl: Backdating to Sunday

From Mike Beane's Blog

Revision as of 12:40, 22 December 2007 by Rabbi Bob (talk | contribs)

Spent a little time on this in a related work project: backdating a date to the Sunday of the same week. Sounded simple at first, however I finally resulted to a dry erase board to map it out before coding it. Funny how leaving the terminal sometimes is a good thing.

The notes
use Date::DayOfWeek;
use Date::Leapyear;

if ($DateA =~ /(\d{4})(\d{2})(\d{2})/)
	{
	my $tmpyear = $1; #Year
	my $tmpmonth = $2; #Month
	my $tmpday = $3; #Day

	#Determine the day of week
	#Sun0,Mon1,Tue2,Wed3,Tr4,Fri6,Sat7

	my $DOW = dayofweek($tmpday, $tmpmonth, $tmpyear);

	#Determine what happens when we subtract the value of
	#the date from the Day.
	#If it is positive, then we remain in the week.
	#If it is Zero, then the date is Sunday and no roll is needed
	#If it is negative, then we've moved back in the previous week
	#If we are previous week, we need to make sure that
	#we check roll to the previous month. If the current month
	#is Jan, we need to roll the year back also.
	
	my $test = $tmpday - $DOW;

	#Positive Outcome
	if ($test > 0)
		{
		$tmpday=$test;
		}

	#Negative Outcome
	elsif ($test < 0)
		{
		### Check for March Roll back to Feb
		### Honor the Leap Year
		if ($tmpmonth =~ m/03/)
			{
			if (isleap($tmpyear))
				{
				$tmpday=(29-abs($test));
				$tmpmonth--;
				}
			else
				{
				$tmpday=(28-abs($test));
				$tmpmonth--;
				}
			}
		#Check for transitions INTO 31 day months
		elsif ($tmpmonth =~ m/02|04|06|09|11/)
			{
			$tmpday=(31-abs($test));
			$tmpmonth--;
			}
		#Check for transitions INTO 30 day months
		elsif ($tmpmonth =~ m/05|07|08|10|12/)
			{
			$tmpday=(30-abs($test));
			$tmpmonth--;
			}
		#Check for transitions from August 
		#Roll both the Month with 31 days
		elsif ($tmpmonth =~ m/08/)
			{
			$tmpday=(31-abs($test));
			$tmpmonth=12;
			}
		#Check for transitions into December
		#Roll both the Month & Year back
		elsif ($tmpmonth =~ m/01/)
			{
			$tmpday=(31-abs($test));
			$tmpmonth=12;
			$tmpyear--;
			}
		}
	#Put the date back together
	$DateA="$tmpyear$tmpmonth$tmpday";

	# Cludge to test to make sure that no new date is greater than 0 and let us know if so
	# Irrelevant to the output
	my $TESTDOW = dayofweek($tmpday, $tmpmonth, $tmpyear);
	if ($TESTDOWN>0)
		{
		print "!\n";
		}
	}