Yeni bir nesne oluşturmadan ve her özelliği el ile ayarlamadan bir LINQ sorgu sonucu nesnesinin bazı özelliklerini değiştirmek istiyorum. Mümkün mü?
Misal:
var list = from something in someList
select x // but change one property
Yeni bir nesne oluşturmadan ve her özelliği el ile ayarlamadan bir LINQ sorgu sonucu nesnesinin bazı özelliklerini değiştirmek istiyorum. Mümkün mü?
Misal:
var list = from something in someList
select x // but change one property
Yanıtlar:
Sorgu sözdiziminin ne olduğundan emin değilim. Ancak burada genişletilmiş LINQ ifade örneği verilmiştir.
var query = someList.Select(x => { x.SomeProp = "foo"; return x; })
Bunun yaptığı anonim bir yöntem ve ifade kullanmaktır. Bu, bir lambdada birkaç ifade kullanmanıza izin verir. Böylece özelliği ayarlama ve nesneyi bu biraz özlü yönteme döndürme işlemlerini birleştirebilirsiniz.
ToList()
hile yapıyor gibi görünüyor. Bunu neden aldýđýndan emin deđilim. Entity Framework ise, bununla da çalışmaz.
Yalnızca tüm öğelerdeki özelliği güncellemek istiyorsanız
someList.All(x => { x.SomeProp = "foo"; return true; })
Bunu tercih ederim. Diğer linq komutlarıyla birleştirilebilir.
from item in list
let xyz = item.PropertyToChange = calcValue()
select item
Bunu yapmanıza engel olan herhangi bir LINQ büyüsü olmamalıdır. Anonim bir tür döndürecek olsa da projeksiyonu kullanmayın.
User u = UserCollection.FirstOrDefault(u => u.Id == 1);
u.FirstName = "Bob"
Bu, gerçek nesneyi de değiştirir:
foreach (User u in UserCollection.Where(u => u.Id > 10)
{
u.Property = SomeValue;
}
Standart sorgu operatörleri ile mümkün değildir - Dil ile Tümleşik Güncelleme değil, Dil ile Tümleşik Sorgudur. Ancak güncellemenizi uzantı yöntemlerinde gizleyebilirsiniz.
public static class UpdateExtension
{
public static IEnumerable<Car> ChangeColorTo(
this IEnumerable<Car> cars, Color color)
{
foreach (Car car in cars)
{
car.Color = color;
yield return car;
}
}
}
Şimdi aşağıdaki gibi kullanabilirsiniz.
cars.Where(car => car.Color == Color.Blue).ChangeColorTo(Color.Red);
UPDATE
, DELETE
ve INSERT
. Bu yüzden anlambilimin bu işlevi engelleyen şey olduğunu iddia etmem.
Öğeleri bir Where
cümle ile güncellemek istiyorsanız , .Where (...) öğesini kullanarak şunları yaparsanız sonuçlarınız kesilir:
mylist = mylist.Where(n => n.Id == ID).Select(n => { n.Property = ""; return n; }).ToList();
Listedeki belirli öğeler için güncellemeler yapabilirsiniz:
mylist = mylist.Select(n => { if (n.Id == ID) { n.Property = ""; } return n; }).ToList();
Herhangi bir değişiklik yapmasanız bile her zaman ürünü iade edin. Bu şekilde listede tutulacaktır.
Sıklıkla yeni bir nesne oluşturmadan bir indeks değeri ve ilk ve son göstergeleri bir listeye dahil etmek istediğimiz yere gideriz. Bu, mevcut sınıfı değiştirmek zorunda kalmadan listenizdeki öğenin konumunu, numaralandırmayı vb. Bilmenizi ve ardından listedeki ilk öğede mi yoksa sonuncusunda mı olduğunuzu bilmenizi sağlar.
foreach (Item item in this.Items
.Select((x, i) => {
x.ListIndex = i;
x.IsFirst = i == 0;
x.IsLast = i == this.Items.Count-1;
return x;
}))
Herhangi bir sınıfı aşağıdakileri kullanarak genişletebilirsiniz:
public abstract class IteratorExtender {
public int ListIndex { get; set; }
public bool IsFirst { get; set; }
public bool IsLast { get; set; }
}
public class Item : IteratorExtender {}
Burada en iyi çözümü düşündüğüm cevabı burada bulamadığım için, bu şekilde:
Verileri değiştirmek için "Seç" kullanmak mümkündür, ancak sadece bir hile ile. Her neyse, bunun için "Seç" yapılmaz. "ToList" ile birlikte kullanıldığında sadece değişikliği gerçekleştirir, çünkü Linq veri gerekmeden yürütmez. Her neyse, en iyi çözüm "foreach" kullanmaktır. Aşağıdaki kodda şunları görebilirsiniz:
class Person
{
public int Age;
}
class Program
{
private static void Main(string[] args)
{
var persons = new List<Person>(new[] {new Person {Age = 20}, new Person {Age = 22}});
PrintPersons(persons);
//this doesn't work:
persons.Select(p =>
{
p.Age++;
return p;
});
PrintPersons(persons);
//with "ToList" it works
persons.Select(p =>
{
p.Age++;
return p;
}).ToList();
PrintPersons(persons);
//This is the best solution
persons.ForEach(p =>
{
p.Age++;
});
PrintPersons(persons);
Console.ReadLine();
}
private static void PrintPersons(List<Person> persons)
{
Console.WriteLine("================");
foreach (var person in persons)
{
Console.WriteLine("Age: {0}", person.Age);
;
}
}
}
"Foreach" dan önce, linq seçimi de yapabilirsiniz ...
var item = (from something in someList
select x).firstordefault();
Alacağı item
ve sonra yapabileceği item.prop1=5;
belirli özelliğini değiştirmek için.
Yoksa db öğelerin bir listesini almak ve prop1
o döndürülen listedeki her öğenin özelliği belirtilen bir değere değiştirmesini istiyor musunuz? Eğer öyleyse bunu yapabilirsin (VB'de yapıyorum çünkü daha iyi biliyorum):
dim list = from something in someList select x
for each item in list
item.prop1=5
next
( list
değişikliklerinizle birlikte iade edilen tüm öğeleri içerir)
for each
döngü yazmak zorunda kalmadan nasıl LINQ deyimi yazmak istediğini düşünüyorum .
2020'de MoreLinq
Pipe
yöntemi kullanıyorum. https://morelinq.github.io/2.3/ref/api/html/M_MoreLinq_MoreEnumerable_Pipe__1.htm
User u = UserCollection.Single(u => u.Id == 1);
u.FirstName = "Bob"