comparing dates in c# taking null value into account - c#

I am new to c#. I am comparing two dates where one is entered by user and the other one is sytem date time. i have the code working as it stands where the obstacle has occured is how to cater for null values. the basic code I have is:
if (mydate.ToShortDateString() != TodaysDate.ToShortDateString())
{
//Error Messaage
}
else
{
//do some code
}
Any feedback will be appreciated

Why are you converting them to strings? Why not just compare the date portions of them as in date1.Date != date2.Date.

You can declare mydate as DateTime?, then it can hold null values.
As to how to handle the error, it depends on whether having a null value for mydate is considered an error or not. If it's an error, you could do:
if (mydate == null || mydate.ToShortDateString() != TodaysDate.ToShortDateString()) {
// error
}
If it's not an error condition, you could do:
if (mydate != null && mydate.ToShortDateString() != TodaysDate.ToShortDateString()) {
// error
}
If you don't declare mydate as DateTime? but instead just declare it as DateTime, then you can check for DateTime.MinValue, like this (DateTime.MinValue is the default value for a DateTime variable):
if (mydate == DateTime.MinValue || mydate.ToShortDateString() != TodaysDate.ToShortDateString()) {
// error
}

Use the ?? operator:
if ((mydate??DateTime.MinValue).ToShortDateString() != TodaysDate.ToShortDateString())
{
//Error Messaage
}
else
{
//do some code
}

Related

Nullable DateTime parameter causes an exception [duplicate]

This question already has answers here:
Linq Query keeps throwing "Unable to create a constant value of type System.Object....", Why?
(5 answers)
Closed 8 years ago.
I'm trying to create an API method, which will allow to filter entries by date. I want to let to use two parameters - startDate and endDate. The second of them optional.
public IEnumerable<Recommendation> GetRecommendationByDate(DateTime startDate, DateTime? endDate)
{
if (endDate == null)
{
endDate = DateTime.Now;
}
var output = db.Recommendations.Where(r => r.IsPublished == true &&
r.CreatedDate.CompareTo(startDate) > 0 &&
r.CreatedDate.CompareTo(endDate) < 0)
.ToList();
return output;
}
After I've added nullable sign, method thows an exception when the second parameter (endDate) isn't null. When it is null, there is not any problems.
Exception sounds:
Unable to create a constant value of type 'System.Object'. Only primitive types or enumeration types are supported in this context.
What is the reason and how to solve it?
Add .HasVale and check if endDate contains the value or not and if it does then use as endDate.Value as shown below
public IEnumerable<Recommendation> GetRecommendationByDate(DateTime startDate, DateTime? endDate)
{
if (endDate == null)
{
endDate = DateTime.Now;
}
var output = db.Recommendations.Where(r => r.IsPublished == true &&
r.CreatedDate.CompareTo(startDate) > 0 &&
r.CreatedDate.CompareTo(endDate.HasValue ? endDate.Value : (The default you want to put when endDate is null)) < 0)
.ToList();
return output;
}

Specified cast is not valid while accessing column value

I am finding records in datatable. If the record matches then I want to compare value in the datarow and do some operation. Please see my code below for better explanation,
foreach (DataRow row2 in dtTo.Rows)
{
DataRow[] match = dtReturn.Select("Id = " + row2["Id"]);
if (match.Length > 0)
{
if (match[0]["boolInt"] == 1) // Getting error on this line
{
match[0]["NewValues"] = "";
}
}
}
I was getting error on below line
if (match[0]["boolInt"] == 1)
Then resharper suggested me to cast to bool. so I changed above line to
if( (bool) (match[0]["bClosed"] = 1))
But when I run the project I get run time error as "Specified cast is not valid" on above line.
In immediate window I get value as 1 when I type ,
(match[0]["bClosed"]
What should i do to get rid of this error?
According this:
No there wont be null. The field is tinyint
you code should look like this (AFAIR, tinyint in SQL server matches byte in CLR):
if ((byte)(match[0]["boolInt"]) == 1)
{
}
If you know the field type, there's no need to call Convert methods. The faster way is to cast directly to that known type.
You need to convert the value to int. You can do it like this:
if (Convert.ToInt32(match[0]["boolInt"]) == 1)
But if the column contains a value that can't be casted you wil get an error.
A better aproach would be:
int number;
bool result = Int32.TryParse(match[0]["boolInt"], out number);
if (result && number == 1)
Try this:
if ((match[0]["boolInt"] as int?) == 1)
{
match[0]["NewValues"] = "";
}
if value is null or not valid int it won't cause exception, but should be handled anyways.

day of week and hour of day in a if statement c#

I want to do something if the day, and time of the day equal true in a if statement. I have the day part down, just can't figure out the time part out. Let say I wan the time to be 9AM.
Here is what I have so far
var dt_check_monday = DateTime.Now.DayOfWeek;
if (dt_check_monday == DayOfWeek.Monday && time_now = DateTime.Now.Hour==9)
{
//do something
}
I can't use this I get an error:
Operator '&&' cannot be applied to operands of type 'bool' and 'System.TimeSpan'
Thanks for any help in advance.
= is an assignment. == is the 'equals'
Your second = should be a ==
You should just do this:
if (DateTime.Now.DayOfWeek == DayOfWeek.Monday && DateTime.Now.Hour == 9)
{
}
Your code has an assignment to an undeclared variable time_now and you're doing an assignment time_now = which is what's causing it to fail.
You should also consider revising how you name your variables, dt_check_monday means absolutely nothing if the value inside it is DayOfWeek.Wednesday, consider changing it to something like dt_currentDayOfWeek but that already exists in the form of DateTime.Now.DayOfWeek which is why I dropped the variable from my example.
I think time_now is having TimeSpan datatype. So you can try this
if (dt_check_monday == DayOfWeek.Monday && time_now.Hours == 9)
{
//do something
}
If you want to keep time_now for later use, you have to encase the assignment in the if-statement with paratheses.
var dt_check_monday = DateTime.Now.DayOfWeek;
if (dt_check_monday == DayOfWeek.Monday && (time_now = DateTime.Now.Hour) == 9)
{
//do something
}

Tricky if statement

Is it possible to convert this if statement into a one line statement ?
if (value != DBNull.Value)
{
dic.Add(columnName);
}
else if (!skipNullValues)
{
dic.Add(columnName);
}
if (value != DBNull.Value || !skipNullValues) dic.Add(columnName);
Use a logical OR:
if (value != DBNull.Value || !skipNullValues)
dic.Add(columnName);
I would keep the addition on a new line for clarity, although for a simple statement like this you're probably alright to drop the curly brackets. You do need to be careful if you try to add more logic in the future though obviously in the branch of the if.
if (!(value == DBNull.Value && skipNullValues))
dic.Add(columnName);
If you edit to include why making it a single line will help you might get a more suitable answer. Here are a few different approaches you could take..
First off, in a single line as you requested:
if ((value != DBNull.Value) || (value == DBNull.Value && !skipNullValues)) { dic.Add(columnName); }
Alternatively you might want to look into using ternary operators if you need something more compact.
var result = (istrue) ? (return valIfTrue) : (return valIfFalse);
More info on ternary operators:
http://msdn.microsoft.com/en-us/library/ty67wk28%28v=vs.80%29.aspx
Most likely (depending on your situation) you should consider creating a method similar to this:
public void AddColumnToDic(object value, string columnName)
bool skipNullValues = false; // todo: read from configuration
if ((value != DBNull.Value) || (value == DBNull.Value && !skipNullValues))
{
dic.Add(columnName);
}
}
and simply call it for every cell value you encounter.

How can this be not equal?

My Goal: Extracting one value from an Excel Range, and verify for these cells' value to be the same within this range;
When a cell's value is not the same as the other, I need to return null.
Here's a piece of code:
internal object GetValueFromCells(string start, string end, Formats format) {
// Verifying for empty or null parameters here and throwing accordingly...
try {
Range cells = Excel.get_Range(start, end) as Range;
object value = null;
bool sameValue = false;
foreach(Range cell in cells) {
// This condition block shall execute only once, since 'value' shall not be null afterwards.
if (value == null || value == DBNull.Value)
if (Formats.Formated == format) {
value = cell.Text;
// The following results to be false !?...
sameValue = value == cell.Text; // Shall this not be true?
} else {
value = cell.Value2;
// The following results to be false !?...
sameValue = value == cell.Value2; // Shall this not be true?
}
// This results being always false!?...
// Shall this not be true, I wonder?
sameValue = Formats.Formated == format ? value == cell.Text : value == cell.Value2;
if(!sameValue)
return null;
}
return value;
} catch (Exception ex) {
// Exception handling...
}
}
Reading this code, I would humbly expect a value to be returned when all of the cells in the range have the same value (for instance 334).
However, this methods always returns null (Nothing in Visual Basic)!
Anyone might explain what I'm missing here while this:
value == cell.Value2
always returns false?
Perhaps is it my algorithm that isn't quite right?
EDIT #1
This has solved the problem:
sameValue = Formats.Formatted == format ? cell.Text.Equals(value) : cell.Value2.Equals(value);
I accepted #Jerod Houghtelling's answer as his answer suggests both the ToString() and the Equals() methods to solve the problem.
In addition to it, I dislike having to call the ToString() method, since the value can be numbers, and comparing numbers under a string looks odd to me. So I prefer the Equals() way which I adopted within my solution.
I would like to thank #Sir Gallahad and #Jerod Houghtelling for their good answers. This was the first time I had to face such a situation, and they both helped me better understand what was going on under the hood, plus the others who contributed too through comments.
And thanks to those who upvoted my question. This serves a purpose to demonstrate that I was not so dumb asking! =P Hehehe...
I'm guessing that cell.Value2 is returning a new instance of an object each time you call it. Therefore I would deduce the == is checking to see if both sides of the equation are the same instance of the object. To actually compare the value stored on both side you will have to use the .Equals or convert the values to something that can be compared, for example a string.
sameValue = value.Equals( cell.Value2 );
/* or */
sameValue = value.ToString() == cell.Value2.ToString();
Also I don't see value being set in your example.
Probably the value == cell.Value2 are comparing objects that are from different instances.
Try value.ToString() == cell.Value2.ToString()

Categories

Resources