Validation of DateTime against another DateTime - c#

I need to ensure that a DateTime variable named start falls approximately a month after the current date. The only means that I am aware of to do this is to create another DateTime variable that is hard-coded to be precisely one month (or four weeks, preferably) after the current date, and compare the two.
Is there a more efficient way to do this, without creating another object that I will do nothing with?

DateTime start = new DateTime(2015, 12, 25);
if (start > DateTime.UtcNow.AddDays(28))
{
// Do something
}

if 4 weeks is a must, then;
if((start-DateTime.Now).Days>=28)
{
}

Related

DateTime to end of the day C#

I receive a date like 1.01.2022 h:00, m:00, s:00, ms: 00
What is the best approach to get the date at the end of the day, something like: 01.01.2022 h:23, m:59, s:59, ms: 999?
I tried those 2 ways:
var endOfDay = new TimeSpan(0, 23, 59, 59, 999);
time = time.Add(endOfDay);
and
time = time.AddDays(1).AddMilliseconds(-1);
This removes all doubt down to the resolution of a single tick. In the code below, assume that dateAndTime could include a non-zero time component.
dateAndTime.Date.AddDays(1).AddTicks(-1);
This
ensures we are only working with a date that has no time component as our reference point/date
moves us to the next date at midnight
subtracts a single tick, bringing us back to our reference date with a full-resolution time component (you could do milliseconds if you prefer, just know it's less resolution).
While this works, it's generally better to consider an alternate design that doesn't rely on a time component at all (e.g. use a given date at midnight on the next day to act as a virtual end-of-day for the given reference date).
If you want just to print out the range, the action format is opinion based. If you, however, want to check if some time is within or without the day, please do it as (note >= and <)
if (timeOfQuestion >= day.Date && timeOfQuestion < day.Date.AddDays(1)) {
...
}
Using onstructions like endOfDays = time.AddDays(1).AddMilliseconds(-1) is dangerous:
please, note that day.Date.AddMilliseconds(999.5) - double value - should be within the day.

AddDays() not working within a while loop

Is there anything that stops the DateTime AddDays() method that doesn't run within a while loop. I have this simple bit of code;
DateTime last_day = monthCalendar2.SelectionRange.End;
DateTime first_day = new DateTime(year, month, day);
//Insert dates into vector
while (first_day != last_day)
{
dates.Add(first_day);
first_day.AddDays(1);
}
I step through the program and first_day never changes, anyone know why?!
The reason being is that DateTime is Immutable, this means that you can't directly modify it and instead need to create a new instance of it. Strings are another type that behave in this way which you may be more used to.
first_day = first_day.AddDays(1);
DateTime is immutable. You should do
first_day = first_day.AddDays(1);
UPDATE:
If you check DateTime.AddDays method description: Returns a new System.DateTime that adds the specified number of days to the value of this instance. That relates to all operations (such as Add, Substract, AddHours etc) on DateTime structure - any calculation does not modify the value of the structure. Instead, the calculation returns a new DateTime structure whose value is the result of the calculation. That's because DateTime is immutable struct. I.e. instance value cannot be changed after it was created.
DateTime can't be changed, so instead do.
first_day = first_day.AddDays(1);

Taking a DateTime value and only accepting time and vice versa

I'm currently developing an application to function as a todo - list and i was wondering how do i accept a Value from a date time box, but only use the value of the date, or the value of the time. I'm currently doing it like this.
DateTime ted = appointmentDateTimeDate.Value; //The date
DateTime at = appointmentDateTimeTime.Value; //The time
should i be doing this another way?
Use DateTime.Date property for date, and DateTime.TimeOfDay for time:
DateTime ted = appointmentDateTimeDate.Date; //The date
TimeSpan at = appointmentDateTimeTime.TimeOfDay; //The time
The BCL doesn't really separate dates and times nicely.
If you're happy to take a new external dependency, I'd like to plug my Noda Time library, which will let you separate things out clearly into LocalDate and LocalTime. To perform the conversion from a date/time picker you'd probably use:
var dateAndTime = LocalDateTime.FromDateTime(appointmentDateTimeDate.Value);
LocalDate date = dateAndTime.LocalDate;
LocalTime time = dateAndTime.LocalTime;
Like others pointed out a DateTime always has both a date and a time component. So although it's possible to save both independently using two DateTime, in most cases it's recommendable to save both together in a single DateTime instance.
You should see if you really need both values separated or if your application could combine both in one property, which will make things easier.
A DateTime value ALWAYS contains both the date and the time, whether you use both or not.
You can use the .Date property of a DateTime to get "just the date". it will still have a time value, but the time value will be midnight. You can also use the .TimeOfDay property to get the time portion, which will be a TimeSpan indicating the number of ticks since midnight.
I'm taking a leap here and assuming you're trying to set the date with one control an d the time with another in the UI. Here's a sample of some code we use to do this using an Ajax CalendarExtender attached to a textbox and a custom TimePicker control.
DateTime dt;
try
{
dt = Convert.ToDateTime(txtViewDate.Text).AddHours(txtViewTime.Hour).AddMinutes(txtViewTime.Minute);
if (txtViewTime.AmPm == MKB.TimePicker.TimeSelector.AmPmSpec.PM)
{
dt = dt.AddHours(12);
}
System.Diagnostics.Debug.WriteLine(dt.ToString());
}
catch (Exception)
{
// abort processing
return;
}

Create a date time with month and day only, no year

I am creating a timer job in VS for sharepoint, and I want to create a Date object that only has a month and day. The reason for this is because I want this job to run annually on the specific date.
If it's not possible with a date object, then how would you go about doing this?
Here's what I've got:
DateTime value = new DateTime(2010, 1, 18);
Well, you can create your own type - but a DateTime always has a full date and time. You can't even have "just a date" using DateTime - the closest you can come is to have a DateTime at midnight.
You could always ignore the year though - or take the current year:
// Consider whether you want DateTime.UtcNow.Year instead
DateTime value = new DateTime(DateTime.Now.Year, month, day);
To create your own type, you could always just embed a DateTime within a struct, and proxy on calls like AddDays etc:
public struct MonthDay : IEquatable<MonthDay>
{
private readonly DateTime dateTime;
public MonthDay(int month, int day)
{
dateTime = new DateTime(2000, month, day);
}
public MonthDay AddDays(int days)
{
DateTime added = dateTime.AddDays(days);
return new MonthDay(added.Month, added.Day);
}
// TODO: Implement interfaces, equality etc
}
Note that the year you choose affects the behaviour of the type - should Feb 29th be a valid month/day value or not? It depends on the year...
Personally I don't think I would create a type for this - instead I'd have a method to return "the next time the program should be run".
How about creating a timer with the next date?
In your timer callback you create the timer for the following year? DateTime has always a year value. What you want to express is a recurring time specification. This is another type which you would need to create.
DateTime is always represents a specific date and time but not a recurring date.
There is no such thing like a DateTime without a year!
From what I gather your design is a bit strange:
I would recommend storing a "start" (DateTime including year for the FIRST occurence) and a value which designates how to calculate the next event... this could be for example a TimeSpan or some custom structure esp. since "every year" can mean that the event occurs on a specific date and would not automatically be the same as saysing that it occurs in +365 days.
After the event occurs you calculate the next and store that etc.
Anyway you need 'Year'.
In some engineering fields, you have fixed day and month and year can be variable. But that day and month are important for beginning calculation without considering which year you are. Your user, for example, only should select a day and a month and providing year is up to you.
You can create a custom combobox using this: Customizable ComboBox Drop-Down.
1- In VS create a user control.
2- See the code in the link above for impelemnting that control.
3- Create another user control and place in it 31 button or label and above them place a label to show months.
4- Place the control in step 3 in your custom combobox.
5- Place the control in setp 4 in step 1.
You now have a control with only days and months. You can use any year that you have in your database or ....

DateTime comparison, minus certain timeframe? c#

Say I have these two DateTime objects:
var dt1 = new DateTime(1900,12,1,1,1,1);
var dt2 = new DateTime(1900, 12, 1, 1, 59, 1);
Obviously if I do DateTime.Compare(dt1,dt2) the method will return a value indicating they do not equal the same (because of the 59/minute component).
If I only want comparison with precision restricted to a certain value (i.e. same day - dont care about hours/minutes etc) is the best way to do this just to rebuild each datetime object?
I.e.
DateTime.Compare(new DateTime(dt1.Year,dt1.Month,dt1.Day,1,1,1),new DateTime(dt2.Year,dt2.Month,dt2.Day,1,1,1))
or is there a smarter way to do this?
There is already a built in function to get the Date from a DateTime, namely the Date property:
DateTime.Compare(dt1.Date,dt2.Date)
In theory you could compare year, month and day in that order instead of building a new DateTime, but since DateTime is a small struct building it is rather cheap, causes no heap allocations etc. And the code is much more readable.
If you just want the same date, just compare the Date properties:
dt1.Date == dt2.Date
If you need down to the same hour, or up to the same month, you need to use the constructors as you've shown.
The same day is easy - just use the Date property:
dt1.Date.CompareTo(dt2.Date)
For other granularities you would probably need to manually build different values though.

Categories

Resources