Reputation: 190
I have the following query:
sqlQuery = 'SELECT MPID, MAPPOINT, X, Y, MPCODE, MultipleSite = 0 FROM MAPPOINT'
var data = context.Database.SqlQuery<WayPoint>(sqlQuery).ToList();
I've pasted the result below.
I'd like to update this result and set MultipleSite
Column to 1 in case there are other rows that has the same X
and Y
values.
For example: records 2 and 3 have the same X
and Y
values, So I would like to update the value of their column MultipleSite
to 1.
Do I have to iterate the result and do some comparison, or I can do it any other way?
The idea is to have a flag that tells me that in that coordinates there are other sites as well.
My class looks like this:
public class WayPoint
{
public int MPID { get; set; }
public string MAPPOINT { get; set; }
public double X { get; set; }
public double Y { get; set; }
public string MPCODE { get; set; }
public bool MultipleSite { get; set; }
}
Upvotes: 1
Views: 194
Reputation: 3676
This can be done in one SQL command...
UPDATE MAPPOINT
SET [MultipleSite] = 1
FROM MAPPOINT m
INNER JOIN (
SELECT X, Y FROM MAPPOINT
GROUP BY X, Y
HAVING COUNT(*) > 1
) gr on gr.X = m.X
and gr.Y = m.Y
And if you just want to select these records to manipulate in memory...
SELECT m.*
FROM MAPPOINT m
INNER JOIN (
SELECT X, Y FROM MAPPOINT
GROUP BY X, Y
HAVING COUNT(*) > 1
) gr on gr.X = m.X
and gr.Y = m.Y
Upvotes: 1
Reputation: 124
Given your data model (i.e., WayPoint
), please try the following:
data.GroupBy(o => new { X = o.X, Y = o.Y })
.Select(g => new
{
Items = g.Select(gp => new WayPoint
{
MPID = gp.MPID,
MAPPOINT = gp.MAPPOINT,
X = g.Key.X,
Y = g.Key.Y,
MPCODE = gp.MPCODE,
MultipleSite = g.Count() > 1
})
}
)
.SelectMany(g=>g.Items)
.ToList();
Upvotes: 1
Reputation: 19121
There are several potential solutions, depending on what you want to achieve, and how you'd prefer to solve it.
You could use something like the following in C# after filling the list data
as in your question, and then use the result to update the DB (if that is what you want to do):
foreach(wayPoint in data)
{
if(data.Any(d => (d.MPID != wayPoint.MPID)
&& (d.X == wayPoint.X)
&& (d.Y == wayPoint.Y)))
{
wayPoint.MultipleSite = 1;
}
}
If you don't need to update the DB, then that should be fine; otherwise, you could either use the result of the above to update your DB, or you might create a stored procedure in the database to do something similar.
One idea:
MPID
, X
, and Y
, and populate it with copies of everything from your main table.if
-structure above (select and get the MPID
-values for all rows with matching X
and Y
-values). MultipleSite
value of 1
).This may sound heavy / slow, and perhaps there are more efficient ways to do what you want, but it should at least be doable and understandable this way.
Either way, I can't see how you can get around iterating over all rows, since that is in essence, exactly what you want to do; to check for each row if there are others with the same values.
Upvotes: 0