How to get Single Row From Query without a foreach Loop? - c#

There is table ViewRight in my database with three columns:
user_id (FK- int)
folder_id(PK-int)
folder_name(varchar(MAX))
I wrote query in c# code to get values of table. I wrote this query below to get values from
ViewRight table of provided user_id.
var query2 = from p in dbContext.ViewRights where p.user_id==user_id select p;
Question I have to use foreach loop to get value of folder_id value of and folder_name of provided user_id. this foreach loop has single value. I don't want to use foreach loop for single value. I there any other approach to get this without using foreach loop.

var vr = query2.SingleOrDefault(x => x.user_id == userid);
if (vr != null)
{
Console.WriteLine(vr.folder_id);
}

Use var vr = query2.SingleOrDefault(x => x.user_id == userid);
if(vr != null) Console.WriteLine(vr.folder_id);
I can't believe John Saunders just copied my answer!

If there is only gonna be one record returned. var query2 = (from p in dbContext.ViewRights where p.user_id==user_id select p).FirstOrDefault();

.SingleOrDefault will get one or more count records
use
.FirstOrDefault();
i chose .FirstOrDefault

Related

LINQ Select Last & Unique Record from a DB using List

I have a table where all vehicles are registered and another table where I have millions of pings for each registered vehicle.
I'm trying to select the last ping from each vehicle that has sent a ping in the last 30 minutes using the LINQ QUERY. I've done the code below through the "for each" idea, but I'm not sure if it is the best way to do.
I would like to know if there is any better way to select this using a single line? I know that I can "group by" them by vehicle_fleetNumber but I couldn't achieve the proper result as the TAKE() is limiting the final result.
var timeRestriction = DateTime.UtcNow.AddMinutes(-30);
var x = _db.Vehicles.Where(r=> r.isActive.Equals(true) && r.helperLastPing > timeRestriction);
foreach (var vehicle in x)
{
var firstOrDefault = _db.Tracks.OrderByDescending(r => r.collectedOn)
.FirstOrDefault(r => r.vehicle_fleetNumber.Equals(vehicle.fleetNumber));
}
return View();
Thank you,
Yes, you should do it in the database by joining both tables and using GroupBy:
var query = from v in _db.Vehicles
join t in _db.Tracks
on v.fleetNumber equals t.vehicle_fleetNumber
where v.isActive && v.helperLastPing > timeRestriction
group t by t.vehicle_fleetNumber into vehicleGroup
select vehicleGroup.OrderByDescending(x => x.collectedOn).First();
foreach(var track in query)
{
// ...
}
Instead of the foreach you can also use query.ToArray or ToList, i don't know what you want to do with it.
If you get moreLinq from nuget you will find the .maxby() method:
for example in a different context:
//get the correct exchange rate
var rateList = _db.lists_ExchangeRates.Where(
rates => rates.Currency == currencyCode);
Decimal? exRate = rateList.MaxBy(rates => rates.LastUpdated).ExchangeRate;
Also see below this gives additional info.
MoreLinq maxBy vs LINQ max + where
In my case if I want the last data that has been save I use this method
var id = db.DPSlips.Max(item => item.Id);
So I thought this might work as will just try
var timeRestriction = DateTime.UtcNow.AddMinutes(-30);
var x = _db.Vehicles.Max(a => a.isActive == true && a.helperLastPing > timeRestriction);

How to write update query using linq to sql in where condition having two column names in c#?

I want to update one column in sql.in where condition two column names are there.
below is mu update query:
string sql = "UPDATE contact set ContactName=#ContactName where ContactID=#ContactId AND UserID=#Userid";
now I want to write using linq.How to write above query using linq.please help me.I tried
var updatequery = (from x in obj.Contacts where x.ContactID == ContactID select x).First();
updatequery.ContactName = ContactName;
obj.SubmitChanges();
but in the above query where condition having only one column name.I want to where condition having two column names.Thanks in advance.
You just have to use the conditional-AND operator &&:
var updateContacts = from x in obj.Contacts
where x.ContactID == ContactID && x.SecondColumn == SecondValue
select x;
// now use First or a loop if you expect multiple
foreach(var contact in updateContacts)
contact.ContactName = ContactName;
obj.SubmitChanges();
I don't know if this will help but you can try this as well.
var updatequery = obj.Contacts
.Where(x => x.ContactID == ContactID && x.SecondColumn == SecondValue)
.FirstOrDefault();
updatequery.ContactName = ContactName;
obj.SubmitChanges();

problem using foreach in linq query result

I have linq query as follows:
var result = (from Customer cust in db select new { userNameList = cust.UserName }).ToList();
i want to loop through each value in the list<>
I tried to use the foreach to accomplish this. It is stupid i could not figure it out
I'm using something like this
foreach (List<string> item in result)
{
if (item.ToString() == userName)
{
userExistsFlag = 1;
}
}
But the .net compiler is just freaking out:
and giving me these errors
Cannot implicitly convert type 'System.Collections.Generic.List' to 'System.Collections.Generic.List'
Cannot convert type 'AnonymousType#1' to 'System.Collections.Generic.List'
Thanks in anticipation
OF ALL THESE IMPLEMENTATIONS WHICH ONE IS MOST EFFICIENT AND CONSUMES LESS RESOURCES.
IT WOULD BE KIND ENOUGH IF SOME ONE CAN CLARIFY THIS FOR ME.
Shorter using Linq:
bool userExistsFlag = result.Any( x=> x.userNameList == userName);
As suggested in the other answers you do not need to project to an anonymous type:
var userNames = (from Customer cust in db select cust.UserName).ToList();
bool userExists = userNames.Contains(userName);
Edit:
The most efficient - if you do not need the set of user names otherwise - is to query the DB directly to check whether the user name exists, so
bool userExists = db.Any( x => x.UserName == userName);
Credit goes to #Chris Shaffer in the comments and #Cybernatet's answer - he was almost there. I would suggest you accept his answer but use Any() ;-)
Try:
var result = (from Customer cust in db select new { userNameList = cust.UserName }).ToList();
userExistsFlag = result.Where(a=> a.userNameList == userName).Count() > 0;
or
userExistsFlag = (
from Customer cust in db
where cust.UserName = userName
select cust
).Count() > 0;
If your query returns a list of names, your FOREACH loop should look like this
foreach( String name in results ){
...
}
Skip using new { userNameList = cust.UserName } which is making it an anonymous instance. You can try
var result = (from Customer cust in db select cust.UserName ).ToList();
if you're just getting the one property and want a list of strings there is no reason to use an anonymous type. code should work like this:
var result = (from Customer cust in db select cust.UserName).ToList();

LINQ statement that returns rownumber of element with id == something?

How to write LINQ statement that returns ROWNUMBER of element with id == something?
There is no direct way to do this that I'm aware of. You'd have to pull the whole query down to the client, and the from there you could project in the row numbers. As an alternative, you could write a stored procedure that uses ROW_NUMBER, and then hit that proc from Linq to SQL.
In your case, the only way you're going to be able to do this would be client side. Keep in mind that the following statement is NOT going to do this at the server, but will pull down your whole table and get the index at the client...
using (var dc = new DataClasses1DataContext())
{
var result = dc.Users
.AsEnumerable() // select all users from the database and bring them back to the client
.Select((user, index) => new // project in the index
{
user.Username,
index
})
.Where(user => user.Username == "sivey"); // filter for your specific record
foreach (var item in result)
{
Console.WriteLine(string.Format("{0}:{1}", item.index, item.Username));
}
}
You should be able to use the Skip and Take extension methods to accomplish this.
For example, if you want row 10:
from c in customers
where c.Region == "somewhere"
orderby c.CustomerName
select new {c.CustomerID, c.CustomerName}
.Skip(9).Take(1);
How To Project a Line Number Into Linq Query Results
How To Project a Line Number Into Linq Query Results

Linq to SQL: DataTable.Rows[0]["ColumnName"] equivalent

Consider this:
var query = from r in this._db.Recipes
where r.RecipesID == recipeID
select new { r.RecipesID, r.RecipesName };
How would i get individual columns in my query object without using a for-loop?
Basicly: how do I translate DataTable.Rows[0]["ColumnName"] into Linq syntax?
It's really unclear what you are looking for, as your two samples are compatible.
As close as I can figure, what you want is:
var rows = query.ToList();
string name = rows[0].RecipesName;
string name = this._db.Recipes.Single(r => r.RecipesID == recipeID).RecipesName;
This is the way to go about it:
DataContext dc = new DataContext();
var recipe = (from r in dc.Recipes
where r.RecipesID == 1
select r).FirstOrDefault();
if (recipe != null)
{
id = recipe.RecipesID;
name = recipe.RecipesName;
}
Sorry, misunderstood your question. As others are saying, you can use ToList() to get a List back. An alternative if all you need is the first one, just use:
query.First().ColumnName
or if you want to avoid an exception on empty list:
var obj = query.FirstOrDefault();
if (obj != null)
obj.ColumnName;
Original Answer (so the comment makes sense):
Use Linq to Datasets. Basically would be something like:
var query = from r in yourTable.AsEnumerable()
select r.Field<string>("ColumnName");

Categories

Resources