Int32.TryParse() or (int?)command.ExecuteScalar() - c#

I have a SQL query which returns only one field - an ID of type INT.
And I have to use it as integer in C# code.
Which way is faster and uses less memory?
int id;
if(Int32.TryParse(command.ExecuteScalar().ToString(), out id))
{
// use id
}
or
int? id = (int?)command.ExecuteScalar();
if(id.HasValue)
{
// use id.Value
}
or
int? id = command.ExecuteScalar() as int?;
if(id.HasValue)
{
// use id.Value
}

The difference between the three performance wise is negligible. The bottleneck is moving the data from the DB to your app, not a trivial cast or method call.
I would go with:
int? id = (int?)command.ExecuteScalar();
if(id.HasValue)
{
// use id.Value
}
It fails earlier, if one day people change the command to return a string or a date, at least it will crash and you will have a chance to fix it.
I would also just go with a simple int cast IF I always expected the command to return a single result.
Note, I usually prefer returning an out param than doing the execute scalar, execute scalar feels fragile (the convention that the first column in the first row is a return value does not sit right for me).

If you expect the command to return null, you should keep in mind that database null (DBNull) is not the same as .NET null. So, conversion of DBNull to int? would fail.
I'd suggest the following:
object result = command.ExecuteScalar();
int? id = (int?)(!Convert.IsDBNull(result) ? result : null);

If none of the above works (especially for users who are battling with MySQL)
why don't you try the following?
int id = Convert.ToInt32(cmd.ExecuteScalar().ToString());

int Result = int.Parse(Command.ExecuteScalar().ToString());
will work in C#.

The latter. Convert.ToInt32() is also an option.

Use id.HasValue for maximum Nullable Type cool-factor!

if ((Int32)cmd.ExecuteScalar () ** 1) //en esta parece qu esta el error pero no lo veo
{
Response.Redirect("Default.aspx");
}
else
{
Response.Redirect("error.htm") ;
}

Related

am using this for Query String to filter the Movies I have in the database there's something wrong

string mid = Request.QueryString["ID"];
if ( db.Movies.Where(i=>i.ID==mid))
{
repMovie.DataSource = db.Movies.Find().ToString();
repMovie.DataBind();
}
Try adding .Any() to return a boolean in your if statement.
Any() returns true if any results are returned by an enumerable object.
if ( db.Movies.Where(i=>i.ID==mid).Any())
{
//...
}
First, db.Movies.Where(i=>i.ID==mid) isn't a boolean. Why are you testing if it's true or false?
Second, repMovie.DataSource = db.Movies.Find().ToString(); has no condition on it. How will that return the right thing? Why don't you do this instead:
(Assuming there's going to be a maximum of one match, ever):
var matchingMovie = db.Movies.FirstOrDefault(i => i.ID == movieId);
if (matchingMovie !== null) {
// you found it in one operation and can work with it now
}
I recommend against variable names like mid. What's that? Anyone else who sees it, or even yourself in a few months, will have no idea and will have to do extra scanning work to figure out its meaning. Use movieId instead.
And for that matter, why are you getting the movieId directly from the querystring yourself? Your MVC action methods should do this for you:
public ActionResult Index(int ID) {
// Lookie! you've automatically gotten the ID from the querystring, and
// you also know it's a non-null integer. If it were null or a non-integer,
// it wouldn't match this route and the client would get a 404, unless you
// had another route to handle those.
}
Alternate ways
int numMid = Convert.ToInt32(mid);
if ( db.Movies.Where(i=>i.ID==numMid).Count()>0)
{
//...
}
or
int numMid = Convert.ToInt32(mid);
if (db.Movies.Any(i=>i.ID==numMid))
{
//...
}

compare object int or dbnull.value linq

I have a linq query:
var capacityQuery = from Info in mySQLDataTable.AsEnumerable()
where Info.Field<object>("location") == Location.ID
orderby Info.Field<DateTime>("date")
The line "where Info.Field("location") == Location.ID" is where I am having problems
My Question is. How do I do a comparison in the where statement that might be either a DBNull.Value or an int value on either side
Below is for reference:
Location is a custom class. The ID returns an object.
private int? addressID;
public object ID {
get
{
if (addressID == null)
return DBNull.Value;
else
return addressID;
}
}
The reason it has to be DBNull is because it is coming from a database. The "table" is also being filled in from a database.
I know == in this case is wrong because its comparing the references which is obviously false.
I know object.equal(var1, var2) should work but it doesnt which im guessing is because they are 2 different objects.
The values could be an int or DBNull both on the table side and the class side.
This is in a foreach loop so I use the same query where Location has an int value or when it has a DBNull value.
Again My Question is. How do I do a comparison in the where statement that might be either a DBNull.Value or an int value on either side
Use
private int? addressID;
public object ID {
get
{
return addressID.HasValue ? addressID.Value as object : DBNull.Value;
}
}
instead. This way, if addressID has not been initialized or if it has been deliberately set to null, the ID property will return a DBNull.Value. Otherwise, it will return an int, but you have to cast it yourself from object to int or int?.
Having said that, creation of the null has been called "a billion dollar mistake" by the author, but by now I think it is in the trillions. You should return an int? datatype from the database if you can, in which case, the comparison will always work. I am not sure which ORM do you use, but Dapper and linq2db handle this scenario correctly as far as I know.

Nullable Int Input string was not in a correct format

I am getting the error:
Input string was not in a correct format.
Some of the Parent Id's can be null. If I comment the ParentId it is successful, so I know it is that line.
var mModel = new MyModel
{
//non nullable
Id = int.Parse(dr["Id"].ToString()),
//nullable
ParentId = int.Parse(dr["ParentId"].ToString()), <--- Throwing the error here
//non nullable
ProductService = dr["MyString"].ToString()
};
I have tried Convert.ToInt32(), and TryParse() and event a ToNullableInt extension Method, but that didnt work.
Check for database null in the dr["ParentId"] and then convert to an int or assign null, like this:
ParentId = !dr.IsDBNull(dr.GetOrdinal("ParentId"))
? dr.GetInt32(dr.GetOrdinal("ParentId"))
: null;
Note: The above code assumes that the ParentId variable is a nullable integer (int? or Nullable<int>.
I don't like calling to string on datareader, moreover, it has methods to get data of specific type
Pattern is
if (!dr.IsDBNull(1)) s = dr.GetString(1)
Or for nullable int:
if (!dr.IsDBNull(1)) i = dr.GetInt32(1)
Note: if you know column name and don't know ordinal or vise-a-versa, you can use GetOrdinal and
GetName methods:
var i = dr.GetOrdinal("ParentId")
var name = dr.GetName(1)
You shouldn't use int.Parse on a value that will not parse correctly... it'll throw an exception.
If you're sure the value will be null or have a valid value, you could try this:
ParentId = String.IsNullOrEmpty(Convert.ToString(dr["ParentId"]))
? (int?)null
: int.Parse(dr["ParentId"].ToString());
You may also want to look into Int32.TryParse, which allows you to try parsing and take some alternative action if the parse fails:
int id;
if (Int32.TryParse(Convert.ToString(dr["ParentId"]), out id)
ParentId = id;
else
ParentId = 0; // the parse failed
Incidentally, I like using Convert.ToString() over .ToString() in most cases, as the former converts null to an empty string, while the latter throws an exception. Just something to consider - doesn't help in this case, as int.Parse("") will throw an exception anyway.

System.InvalidCastException: Specified cast is not valid. Error

I am on a C# ASP.NET project.
I have a MySQL table with a userid field of type int.
Now I want to get the number of rows where value of userid equals certain value using LINQ.
To achieve this, I wrote the following method:
public int getCount(int usercode) {
int count = 0;
DataTable mytable = getAllRowsAndReturnAsDataTable(); // assigning a DataTable value to mytable.
if (mytable.Rows.Count > 0) {
count = (from x in mytable.AsEnumerable() where x.Field<Int32>("userid") == usercode select x).Count();
}
return count;
}
but it is showing error System.InvalidCastException: Specified cast is not valid. showing count = (from x in mytable.AsEnumerable() where x.Field<Int32>("userid") == usercode select x).Count(); in red highlight area.
I don't know what I did wrong here. Please help.
The most likely cause of the InvalidCastException is the x.Field<Int32>("userid") line. The Field<T> extension method will throw an InvalidCastException in the case where the actual type of the data doesn't match the type which was passed to Field<T>. Hence if userid wasn't an Int32 this would throw.
EDIT
Based on your comments the type of userid is actually UInt32 and not Int32. This is what is causing the problem. Try using the following and it should work
x.Field<UInt32>("userid")
Without looking at the data coming back from your database I can only guess that the following part of your LINQ is at fault:
x.Field<Int32>("userid")
Your userid column value probably isn't an int, I would put my money on it being NULL?
UPDATE: Can you confirm it's not the Field call that is breaking? Simply change your code to something like this without the Field call:
public int getCount(int usercode){
int count = 0;
DataTable mytable = getAllRowsAndReturnAsDataTable(); // assigning a DataTable value to mytable.
if (mytable.Rows.Count > 0) {
count = mytable.AsEnumerable().Count(); // No WHERE function call so no casting.
}
return count;
}
You could also inspect what the values are that are returned by mytable.AsEnumerable() in a watch window for example to ensure that everything looks correct. If the code above works then it's the Field call blowing up. Find out which row cannot be cast to an Int32 and go from there.
If it is in fact NULL, there are a number of ways you can solve this.
Make sure you don't return NULL from your database query, in MySQL you can use IFNULL.
Use a nullable type for the generic being passed into Field:
where x.Field("userid") == (Int32?)usercode

Specified cast is invalid error, LINQ to Oracle table

Oracle column: user_id int not null,
Linq query:
UserId = user.Field<int>("user_id"),
UserId is int type. Other string, char fields are workign fine, only when I use thsi field I get this error.
What is the correct mapping or anythign I am doing wrong ?
If you're using Field<T>() then that suggests you're using a DataTable, at which point the database type is mostly irrelevant. The exception should show you how the cast has failed - what the actual type is. If it doesn't, you can easily put some diagnostics in though:
object o = user["user_id"];
if (o == null)
{
Console.WriteLine("user_id is null");
}
else
{
Console.WriteLine("Actual type of user_id: {0}", o.GetType());
}
I suspect you'll find it's long or short, or something like that - but this should show you for sure.

Categories

Resources