22001

Change a list's property using linq

Question:

How to make the following code shorter, perhaps using anonymous method or extensions and LINQ.

Since I have to repeat this code several times and I want to make it as succinct as possible.

var imagesToUnlock = App.ImageListVM.Items.Where(img => img.Category == key); foreach (var image in imagesToUnlock) { image.IsLocked = false; }

Answer1:

The other solutions here feel dirty because they mutate objects in a collection via the use of LINQ.

I would instead, put the code and the filter condition into an extension method and call that:

public static IEnumerable<Item> UnlockWhere(this IEnumerable<Item> list, Func<Item, bool> condition) { foreach (var image in list) if (condition(image)) { image.IsLocked = false; yield return image; } }

The keeps the immutability-concerns of LINQ intact and still produces the expected result.

The call becomes:

var unlockedItems = App.ImageListVM.Items.UnlockWhere(img => img.Category == key);

<strong>EDIT</strong>

Re-written to completely remove LINQ. Instead, this new method iterates only once and returns a new, mutated collection.

Answer2:

Not the most efficient way to do it, but I believe you can do

var imagesToUnlock = App.ImageListVM.Items.Where(img => img.Category == key).ToList().Foreach(f => f.IsLocked = false);

Check out the <a href="http://msdn.microsoft.com/en-us/library/bwabdf9z%28v=vs.110%29.aspx" rel="nofollow">Foreach</a> method on List<T> for more info.

I would also like to note (as some have pointed out in the comments) that this is not considered best practice by some people. You should take a look at <a href="http://blogs.msdn.com/b/ericlippert/archive/2009/05/18/foreach-vs-foreach.aspx" rel="nofollow">this article</a> by Eric Lippert, who explains the issue in better detail.

Answer3:

<strong>Here's a stab as an extension method</strong>

<strong>Code</strong>

public static IEnumerable<T> SetPropertyValues<T>(this IEnumerable<T> items, Action<T> action) { foreach (var item in items) { action(item); yield return item; } }

<strong>Usage</strong>

private class Foo { public string Bar { get; set; } } [TestMethod] public void SetPropertyValuesForMiscTests() { var foos = new[] { new Foo { Bar = "hi" }, new Foo { Bar = "hello" } }; var newList = foos.SetPropertyValues(f => f.Bar = "bye"); Assert.AreEqual("bye", newList.ElementAt(0).Bar); Assert.AreEqual("bye", newList.ElementAt(1).Bar); }

I tested it and it works fine.

Answer4:

Yeah you can do this. Adapted from this <a href="https://stackoverflow.com/questions/398871/update-all-objects-in-a-collection-using-linq" rel="nofollow">answer</a>.

imagesToUnlock.Select(i => {i.IsLocked = false; return i;}).ToList();

Edit: A lot of people are saying this is bad practice. I agree with <a href="https://stackoverflow.com/a/16594601/703644" rel="nofollow">dasblinkenlight</a> here.. Exploring the limits of LINQ and C# is our duty as programmers. It isn't unreasonable to change the objects type from the DTO to the view model or domain object, I know its not the best, but if encapsulated and commented it isn't the end of the world to use select to do this. But please be conscious of the best practices explained by <a href="http://blogs.msdn.com/b/ericlippert/archive/2009/05/18/foreach-vs-foreach.aspx" rel="nofollow">Eric.</a>

Recommend

  • Eliminate Duplicate C# Property Bodies
  • Python are strings immutable [duplicate]
  • Is func_globals mutable?
  • REACT: Add highlighted border around selected image [closed]
  • Postgres psql output strings without escape characters
  • Run an exe in client machine from a website
  • What's effective way to write Vaadin project ?
  • How to get floated divs align to the top?
  • GhostScript PDF Merging (Losing Editable Fields)
  • Does data used by an app get deleted when a user installs an update?
  • deploy SQL Server Database with a Winforms app
  • Counterintuitive design of addition/subtraction between numbers and nullable numbers [closed]
  • Optional parameter in UriTemplate in WCF
  • Cassandra: What is a subcolumn
  • Deleting a widget from QTableView
  • Fat binaries in iOS
  • How to convert integer to string and get length of string
  • multidatatrigger with multibinding in ControlTemplate.Triggers
  • Is there a parser equivalent of 'fragment' marking in ANTLR4?
  • Put value at centre of bins for histogram
  • Trying to string.Join an IList
  • Cannot get the UserManager class
  • Linq Merge lists
  • Build Successful but not running on simulator
  • How can I extract results of aggregate queries in slick?
  • PHP buffered output depending on server setting?
  • Functions in global context
  • Set the selected item in dropdownlist in MVC3
  • Is possible to count alias result on mysql
  • Check if a string to interpolate provides expected placeholders
  • json Serialization in asp
  • Django query for large number of relationships
  • Programmatically clearing map cache
  • costura.fody for a dll that references another dll
  • Why is Django giving me: 'first_name' is an invalid keyword argument for this function?
  • Observable and ngFor in Angular 2
  • How can I use `wmic` in a Windows PE script?
  • UserPrincipal.Current returns apppool on IIS
  • java string with new operator and a literal
  • How to push additional view controllers onto NavigationController but keep the TabBar?