I'm programming in Visual studio 2013 C#.
If listname.add is adding a number, so how to remove a number from a list?
The complement of "add" is not "subtract" for a list, it's "remove".
To remove an item with a specific value you can use the Remove method:
listname.Remove(value);
To remove an item at a specific index you can use the RemoveAt method:
listname.RemoveAt(index);
To remove multiple values you can use the RemoveAll method, which will remove all items that match a condition:
listname.RemoveAll(i => i == value);
Note that the Remove method will search through the list until it finds the value. If this is something that you do frequently, you might want to use differnt collection, like a HashSet<int> where removing a value is an O(1) operation instead of an O(n) operation.
thanks you all guys. Guffa solved it. you just need to enter "listname.Remove(value);" its my first question here. and I'm going to come back. for those who wondering- I'm developing A game. I I needed a list to set my levels system, thanks for your help!
Related
I am trying to solve a string manipulation problem where I need to store characters in a collection that doesn't allow duplicates. So I am using HashSet, however I have noticed that when I am adding characters to it, hashset is getting sorted automatically.
For ex: I had characters 'b' and 'c' in the set already at index 0 and 1 but when I added character 'a' it got added to the index 0 shifting characters 'b' and 'c' to the right at indexes 1 and 2 respectively.
I was under the impression that Hashset are suppose to be not sorted.
please explain the reason behind this behavior and what else should I use if HashSet is working as it is suppose to be.
Thanks
From HashSet<T> Class:
A HashSet collection is not sorted and cannot contain duplicate elements. If order or element duplication is more important than performance for your application, consider using the List class together with the Sort method.
The change in order is due to hashing. Consider using a Dictionary to store the indices along with the characters, Dictionary keys can't be duplicates.
I found this:
This is what I found on google
So far I have
#if (!(Model.CurrentVersion.LRC.List == Model.PrevVersion.LRC.List))
I want to see if the list from the previous version matches the current version however this only returns true (with the !). Both of the lists are empty but it's not returning false.
Is there a better way of seeing if lists match? And why is it always returning true?
Thanks!
You need to check if the content of the lists are equal. There are several ways of doing so.
If the order of items is important then try
SequenceEqual
#if(!Model.CurrentVersion.LRC.List.SequenceEqual(Model.PrevVersion.LRC.List))
If you don't care about the order of the items in the lists you could use
!ints1.All(ints5.Contains)
Now you still have the problem that you are comparing if the items in the list are the same objects. You might want to check if theses items equal in content. For that you need to implement an IEqualityComparer<T>. In the SequenceEqual page there is a great example to implement this case.
I don't usually develop on Windows but recently I have had to do a bit of work with C# and I'm trying to get my head around a few things. I've been looking through the MSDN but cant quite find what I'm looking for.
Anyway as I understand it a List is indexed, much like an array. However if I deleted an item at position X using RemoveAt() would it then shift all the items so that a new item now filled position X? Or would position X just be empty?
Also using Remove() seems fairly straight forward if you have a List of strings or integers, but if you have a list of objects is it possible to use Remove() to delete an item where an object field has a specific value?
For example
Say i have List where each car object has a make, model & color.
Could i do something along the lines of
cars.Remove(cars.color="red");
I'm sure that is horribly wrong but I am coming from a PHP background so im pretty confused about alot of the syntax at the moment.
Thanks
List<T> will not get holes.
Removing an item will shift all subsequent items up by one.
You can remove all items that match a condition by calling RemoveAll() with a lambda expression:
list.RemoveAll(o => o.Color == "Red");
if I deleted an item at position X using RemoveAt() would it then
shift all the items so that a new item now filled position X?
Yes.
if you have a list of objects is it possible to use Remove() to delete
an item where an object field has a specific value?
Yes, use the RemoveAll method:
cars.RemoveAll(c => c.color == "red");
When items are removed the spot is taken up by the next one. As lists are collections you can use lambda with remove all
Cars.RemoveAll( x=> x.colour == "red");
Will remove all re cars.
This question already has answers here:
Closed 12 years ago.
Possible Duplicates:
Exception during iteration on collection and remove items from that collection
How to remove elements from a generic list while iterating around it?
Better way to remove matched items from a list
// tmpClientList is List<Client> type
if (txtboxClientName.Text != "")
foreach (Client cli in tmpClientList)
if (cli.Name != txtboxClientName.Text)
tmpClientList.Remove(cli);
Error: "Collection was modified; enumeration operation may not execute."
How can i remove items from the list, in some simple way, without saving indexes of these items in another list or array, and removing them in another place in the code. Tried also RemoveAt(index) but it's exactly the same situation, modifying when loop runs.
Move backwards through the list.. that way removing an item does not affect the next item.
for(var i=tmpClientList.Count-1;i>=0;i--)
{
if (tmpClientList[i].Name != txtboxClientName.Text)
tmpClientList.RemoveAt(i);
}
On a List<T>, there is a RemoveAll method that takes a delegate to indicate whether to remove the item. You can use it like this:
tmpCLientList.RemoveAll(cli => cli.Name != txtboxClientName.Text);
Either use a for/while loop, or tmpClientList.RemoveAll(a => a.Name == txtboxClientName.Text). As you didn't specify which c# version you are using, ymmw.
Don't use foreach. Use for and descend the list (i.e. start from the end), using RemoveAt.
So,
// tmpClientList is List<Client> type
if (txtboxClientName.Text != "")
foreach (int pos = tmpClientList.Length - 1; pos >= 0; pos--)
{
Client cli = tmpClientList[pos];
if (cli.Name != txtboxClientName.Text)
tmpClientList.RemoveAt(pos);
}
The problem is that you are trying the modify the list in a foreach iteration. Replace that with a for and you should be ok.
Also, since you seem to be using user input for the name, consider cleaning up the input a bit, at least with a Trim() to remove extra white spaces. If you don't, 'John ' and 'John' will be two different things.
Same for the initial != "" check.
You can create another list with the items you want to delete and iterate the new list to remove items from your "txtboxClientName" list.
Actually, foreach uses Enumerators to iterate through given Item-Collections. Going further the System.Collections.Generic.List<T> implements the IEnumarable-Interface to provide a Class, that knows how to iterate through the items of the list, i.e. the Enumerator. Now if you iterate through that list by using foreach the Enumerator keeps track of the current position, how to reach the next position and some other stuff. The internal logic could be something like storing the number of items in a variable n and then access all objects from 0 to n-1. As you may notice if any object is removed between the iteration steps we shall end in a NullReferenceException when the Enumerator tries to deliver the last object of the list. So to prevent any iteration failures, the list itself is not allowed to be modified during Enumeration.
Hope I was able to state that out at least a little bit comprehensively. :-)
I have an array of items that are time sensitive. After an amount of time, the last item needs to fall off and a new item is put at the beginning.
What is the best way to do this?
I would suggest using a queue, just a special instance of an array or list. When your timed event occurs, pop the last item from the queue, and then push your new item on.
Probably the easiest way to do this with an array is to use a circular index. Rather than always looking at array[n], you would reference array[cIndex] (where cIndex referrs to the item in the array being indexed (cIndex is incremented based on the arraySize (cIndex % arraySize)).
When you choose to drop the oldest item in the array, you would simply reference the element located at ((cIndex + (arraySize - 1)) % arraySize).
Alternatively, you could use a linkedList approach.
Use a Queue instead.
By using a Queue, preferably one implemented using a linked-list.
Have a look at using a Queue rather than a simple array.
A queue would work if there a fixed number of items.
Given that the 'amount of time' is known, how about a SortedDictionary with a DateTime key and override the Add method to remove all items with keys that are too old.
LinkedList<T> has AddFirst and RemoveLast members that should work perfectly.
EDIT: Looking at the Queue docs, it seems they use an internal array. As long as the implementation uses a circular-array type algorithm performance should be fine.
In csharp 3 you can do:
original = new[] { newItem }.Concat(
original.Take(original.Count() - 1)).ToArray()
But you are probably better off using a specialised datastructure
Queue is great for FIFO arrays. For generic array handling, use List(T)'s
Insert(0, x) and RemoveAt(0) methods to put or remove items in front of the list, for example.
Technically you need a deque. A queue has items pushed and popped off one end only. A deque is open at both ends.
Most languages will allow array manipulation, just remove the first element and put another one on the end.
Alternatively you can shift every element, by looping. Just replace each element (starting from the oldest) with its neighbour. Then place the new item in the last element.
If you know that your deque won't go above a certain size, then you can make it circular. You'll need two pointers to tell you where the two ends are though. Adding and removing items, will increase/decrease your pointers accordingly. You'll have to detect a buffer overflow condition (i.e. your pointers 'cross'). And you'll have to use modular arithmetic so your pointers go in a circle around the array.
Or you could time stamp each element in the array and remove them when they become too 'old'. You can either do this by keeping a separate array indexed in the same way, or by having an array of two element arrays, with the time stamp stored in one of the sub-elements.
If you're looking for the fastest way of doing this, it's going to be a circular array: you keep track of your current position in the array (ndx), and the end of the array (end), so when you insert an item, you implicitly eliminate the oldest item.
A circular array is the fastest implementation of a fixed-size queue that I know of.
For example, in C/C++ it would look like this for ints (quitting when you get a 0):
int queue[SIZE];
int ndx=0; // start at the beginning of the array
int end=SIZE-1;
int newitem;
while(1){
cin >> newitem;
if(!newitem) // quit if it's a 0
break;
if(ndx>end) // need to loop around the end of the array
ndx=0;
queue[ndx] = newitem;
ndx++
}
Lots of optimization could be done, but if you want to built it yourself, this is the fastest route.
If you don't care about performance, use a shipped Queue object because it should be generalized.
It may or may not be optimized, and it may not support a fixed size list, so be sure to check the documentation on it before using.