Unoffical empeg BBS

Quick Links: Empeg FAQ | RioCar.Org | Hijack | BigDisk Builder | jEmplode | emphatic
Repairs: Repairs

Topic Options
#146573 - 03/03/2003 13:19 Can someone figure this out for me?
JeffS
carpal tunnel

Registered: 14/01/2002
Posts: 2858
Loc: Atlanta, GA
Here’s what I’d like to do.

Given:
The total number of days in a range of dates
The first day as an integer (i.e. Thursday= 4)
X is my input value representing a day of the week (i.e. Sunday = 0)

I Want:
The number of times X is contained in the range of days.

Example:
Number of days = 16
Starting day = Thursday
X = Sunday
Answer = 2

I just want to know if there’s a simple way to do this with mathematics (not If->Then logic). I had a long weekend and my brain is tired so I can’t figure out how to do this, or even if it’s possible. I’m probably going to go ahead and write a function to do it with If-Then, but if anyone can give me a mathematical answer I’d appreciate it as this is really bugging me.
_________________________
-Jeff
Rome did not create a great empire by having meetings; they did it by killing all those who opposed them.

Top
#146574 - 03/03/2003 14:03 Re: Can someone figure this out for me? [Re: JeffS]
jimhogan
carpal tunnel

Registered: 06/10/1999
Posts: 2591
Loc: Seattle, WA, U.S.A.
Dang, this almost worked but not quite:

INT(((7+X-StartDay+DurationInDays)/7)-1))

I'm assuming you have an INT/ROUND function at your disposal. Do you have an offset system date/days function?
_________________________
Jim


'Tis the exceptional fellow who lies awake at night thinking of his successes.

Top
#146575 - 03/03/2003 14:23 Re: Can someone figure this out for me? [Re: jimhogan]
JeffS
carpal tunnel

Registered: 14/01/2002
Posts: 2858
Loc: Atlanta, GA
I'm working in Pascal, so I do have Round, Trunc, mod, etc. functions. As for the second question, Delphi 7 has a great host of date functions available, if that's what you're asking. The code currently builds up an array by looping through all the days and populating an array, but this is what I'd like to change. It just seems to me I should be able to do it with math functions.
_________________________
-Jeff
Rome did not create a great empire by having meetings; they did it by killing all those who opposed them.

Top
#146576 - 03/03/2003 14:47 Re: Can someone figure this out for me? [Re: JeffS]
Roger
carpal tunnel

Registered: 18/01/2000
Posts: 5683
Loc: London, UK
I think this'll work (C++):

/** Given a run of days, length total_days, starting on
* start_day_of_week, where 0=Sunday, 6=Saturday, return the number of
* days that are a particular day, given by find_day_of_week
*/
int dayCount(int total_days, int start_day_of_week, int find_day_of_week)
{
if (total_days == 0)
return 0;

int total_weeks = total_days / 7;
int days_remaining = total_days % 7;

// If I've got entire weeks, then I've got one find_day_of_week in
// each.

// To see if our remaining days contain the one we're looking for
// we 'unmodulo' the maths, and then do a range comparison.
if (find_day_of_week < start_day_of_week + days_remaining)
return total_weeks + 1;

return total_weeks;
}

_________________________
-- roger

Top
#146577 - 03/03/2003 14:50 Re: Can someone figure this out for me? [Re: JeffS]
wfaulk
carpal tunnel

Registered: 25/12/2000
Posts: 16706
Loc: Raleigh, NC US
d = total days
s = start day (0-6)
t = target day (0-6)

x = ( d div 7 ) + ( ( ( ( d % 7) - ( ( ( 7 - s ) + t ) % 7 ) ) % 7 ) + 1 )

I think that's right.

d div 7 gives the number of full weeks, so the target day should be in each of those.

d % 7 gives the number of days past the last full week.

( ( ( 7 - s ) + t ) % 7 ) should give the day difference between the start day and the target day.

The difference of those two should be -6 to 6, inclusive. If it's negative, then it didn't get to the target day again. If it's non-negative, then it did.

Taking the % 7 of that difference should return -1 or 0 in the two above cases.

Adding one to that gives 0 or 1, 0 if the day wasn't reached, 1 if it was.

I haven't tested fully, but that should get you most of the way there.
_________________________
Bitt Faulk

Top
#146578 - 03/03/2003 14:51 Re: Can someone figure this out for me? [Re: Roger]
wfaulk
carpal tunnel

Registered: 25/12/2000
Posts: 16706
Loc: Raleigh, NC US
do this with mathematics (not If->Then logic)
if (find_day_of_week < start_day_of_week + days_remaining)

Hmmm.
_________________________
Bitt Faulk

Top
#146579 - 03/03/2003 14:55 Re: Can someone figure this out for me? [Re: wfaulk]
Roger
carpal tunnel

Registered: 18/01/2000
Posts: 5683
Loc: London, UK
It's only one if-then, and this is Pascal. It's not like there's a loop, which is surely the bigger problem.

Anyway, my solution is off-by-one on a couple of points in the problem space. Ignore it anyway.
_________________________
-- roger

Top
#146580 - 03/03/2003 14:59 Re: Can someone figure this out for me? [Re: JeffS]
rompel
stranger

Registered: 26/08/2000
Posts: 44
Loc: California
In C:

((Start - X + 6) % 7 + NumDays) / 7

It's been 18 years since I've written any Pascal, but it should be something like:

Trunc((((Start - X + 6) Mod 7) + NumDays)/7)

Some testing will, obviously, be required.

--John

Top
#146581 - 03/03/2003 15:02 Re: Can someone figure this out for me? [Re: wfaulk]
Roger
carpal tunnel

Registered: 18/01/2000
Posts: 5683
Loc: London, UK
Unless there's something wrong with the slowDayCount function in the attached, then Bitt's code doesn't work quite right, either.



Attachments
144616-days.cpp (105 downloads)

_________________________
-- roger

Top
#146582 - 03/03/2003 15:02 Re: Can someone figure this out for me? [Re: wfaulk]
JeffS
carpal tunnel

Registered: 14/01/2002
Posts: 2858
Loc: Atlanta, GA
Thanks, I'll test this to make sure. This looks like the road I was going down, but it started looking complicated so I figured I was doing something wrong.

Now comes the question of code readability. . .
_________________________
-Jeff
Rome did not create a great empire by having meetings; they did it by killing all those who opposed them.

Top
#146583 - 03/03/2003 15:04 Re: Can someone figure this out for me? [Re: Roger]
wfaulk
carpal tunnel

Registered: 25/12/2000
Posts: 16706
Loc: Raleigh, NC US
Like I said, I didn't test it, but it ought to be close.
_________________________
Bitt Faulk

Top
#146584 - 03/03/2003 15:05 Re: Can someone figure this out for me? [Re: JeffS]
wfaulk
carpal tunnel

Registered: 25/12/2000
Posts: 16706
Loc: Raleigh, NC US
code readability
Well, in C, I'd say macros would be your friend, but I don't know what kind of preprocessors exist in Pascal world.
_________________________
Bitt Faulk

Top
#146585 - 03/03/2003 15:07 Re: Can someone figure this out for me? [Re: wfaulk]
revlmwest
addict

Registered: 05/06/2002
Posts: 497
Loc: Hartsville, South Carolina for...
In reply to:

I don't know what kind of preprocessors exist in Pascal world.


I wasn't aware that Pascal world still existed....
_________________________
Michael West

Top
#146586 - 03/03/2003 15:12 Re: Can someone figure this out for me? [Re: wfaulk]
JeffS
carpal tunnel

Registered: 14/01/2002
Posts: 2858
Loc: Atlanta, GA
No preprocessor unfortunately, and normally this doesn't bother me. I generally dislike macros when I write in C, but this is one time that a solid macro would be very beneficial.
_________________________
-Jeff
Rome did not create a great empire by having meetings; they did it by killing all those who opposed them.

Top
#146587 - 03/03/2003 15:16 Re: Can someone figure this out for me? [Re: revlmwest]
JeffS
carpal tunnel

Registered: 14/01/2002
Posts: 2858
Loc: Atlanta, GA
Yes, though it's only really used in Delphi now. Delphi's a great development tool that is much more powerful than people give it credit for. There are very few times I get frustrated about not being able to do something I'd be able to do in C (like the aforementioned macros) but I can develop apps in a quarter of the time it took me in C++, without writing shoddy code.
_________________________
-Jeff
Rome did not create a great empire by having meetings; they did it by killing all those who opposed them.

Top
#146588 - 03/03/2003 15:19 Re: Can someone figure this out for me? [Re: JeffS]
wfaulk
carpal tunnel

Registered: 25/12/2000
Posts: 16706
Loc: Raleigh, NC US
I can develop apps [in pascal] in a quarter of the time it took me in C++
My crappy language is better than your crappy language!

_________________________
Bitt Faulk

Top
#146589 - 03/03/2003 15:22 Re: Can someone figure this out for me? [Re: wfaulk]
JeffS
carpal tunnel

Registered: 14/01/2002
Posts: 2858
Loc: Atlanta, GA
My crappy language is better than your crappy language!

Heh, actually C++ is clearly the better language as far as I'm concerned. I just think Borland makes better development tools than M$. Now outside of Windows development it's another story altogether.
_________________________
-Jeff
Rome did not create a great empire by having meetings; they did it by killing all those who opposed them.

Top
#146590 - 03/03/2003 15:29 Re: Can someone figure this out for me? [Re: JeffS]
Roger
carpal tunnel

Registered: 18/01/2000
Posts: 5683
Loc: London, UK
Right, this one definitely works (assuming my slowDayCount function is correct):

/** Given a run of days, length total_days, starting on
* start_day_of_week, where 0=Sunday, 6=Saturday, return the number of
* days that are a particular day, given by find_day_of_week
*/
int dayCount(int total_days, int start_day_of_week, int find_day_of_week)
{
if (total_days == 0)
return 0;

int total_weeks = total_days / 7;
int days_remaining = total_days % 7;

// If I've got entire weeks, then I've got one find_day_of_week in
// each.

// The run of days remaining starts at start_day_of week and ends
// at start_day_of_week + days_remaining - 1
if ((((find_day_of_week + 7) - start_day_of_week) % 7) < days_remaining)
return total_weeks + 1;

return total_weeks;
}

It's still got those two 'if' statements in it. Your call. I think that the problem with Bitt's solution (or, strictly, my implementation of it) is that the C/C++ % operator does odd things with negative numbers.


Attachments
144630-days.cpp (123 downloads)

_________________________
-- roger

Top
#146591 - 03/03/2003 15:32 Re: Can someone figure this out for me? [Re: rompel]
Roger
carpal tunnel

Registered: 18/01/2000
Posts: 5683
Loc: London, UK
((Start - X + 6) % 7 + NumDays) / 7

Yep. That one works. You win.

_________________________
-- roger

Top
#146592 - 03/03/2003 15:36 Re: Can someone figure this out for me? [Re: Roger]
JeffS
carpal tunnel

Registered: 14/01/2002
Posts: 2858
Loc: Atlanta, GA
Excellent, I'll tranlate this into Pascal and see how it handles the Mod stuff. Either way you've all been a big help. Not only did you build me a great MP3 player, now you're writing my code for me!
_________________________
-Jeff
Rome did not create a great empire by having meetings; they did it by killing all those who opposed them.

Top
#146593 - 03/03/2003 15:38 Re: Can someone figure this out for me? [Re: rompel]
JeffS
carpal tunnel

Registered: 14/01/2002
Posts: 2858
Loc: Atlanta, GA
Ouch, totally missed your post. I suppose it was too simple!
_________________________
-Jeff
Rome did not create a great empire by having meetings; they did it by killing all those who opposed them.

Top
#146594 - 03/03/2003 15:38 Re: Can someone figure this out for me? [Re: Roger]
rompel
stranger

Registered: 26/08/2000
Posts: 44
Loc: California
In reply to:


I think that the problem with Bitt's solution (or, strictly, my implementation of it) is that the C/C++ % operator does odd things with negative numbers.




Yeah, that's why my solution has a +6 instead of a -1.

Top
#146595 - 03/03/2003 15:39 Re: Can someone figure this out for me? [Re: Roger]
rob
carpal tunnel

Registered: 21/05/1999
Posts: 5335
Loc: Cambridge UK
OK, now obfuscate it!

Top
#146596 - 04/03/2003 02:19 Re: Can someone figure this out for me? [Re: rob]
canuckInOR
carpal tunnel

Registered: 13/02/2002
Posts: 3212
Loc: Portland, OR
OK, now obfuscate it!


What... you mean write it in perl?

Top
#146597 - 04/03/2003 09:09 Re: Can someone figure this out for me? [Re: JeffS]
JeffS
carpal tunnel

Registered: 14/01/2002
Posts: 2858
Loc: Atlanta, GA
Just as an update:

Having gotten sidetracked onto a different project at the end of yesterday (darn multitasking) I've only now been able to verify the answer:

((((StartingDay - FindDay + 6) Mod 7) + TotalDays) div 7);

Rompel was correct, though in the Pascal implementation the "Div" makes a Trunc unnecessary.

Thanks again to all, I'll feel much better about the way this works now. (The existing solution built up an array in global memory by the slow method. I didn't care for this as it really divorced the computation from the usage as well as requiring an unnecessary global variable).
_________________________
-Jeff
Rome did not create a great empire by having meetings; they did it by killing all those who opposed them.

Top