I ran into this problem today: I got an array with Account objects. I need
to iterate through this array to supplement the accounts in the array with
more data. But the compiler complains when I try to modify the objects in
the array while iterating through it. I marked the bugs in this code:
// Loop through all previously added accounts
foreach(Account a in a1) // a1 is an ArrayList
{
// If name and context is the same
if(a.Name == name && a.Context == context)
{
// Add the amount to the existing account object in the array
a.Amount += amount; // BUG!
break;
}
else
{
// Add a new account object to the array
Account newAccount = new Account(name, ns, context, amount);
a1.Add(newAccount); // BUG!
}
}
There is an outer loop where name, context and amount are found. Hope I
provided enough info. What is the right way of doing this?
Gustaf 6 6030
Gustaf Liljegren <gu**************@bredband.net> wrote: I ran into this problem today: I got an array with Account objects. I need to iterate through this array to supplement the accounts in the array with more data. But the compiler complains when I try to modify the objects in the array while iterating through it. I marked the bugs in this code:
// Loop through all previously added accounts foreach(Account a in a1) // a1 is an ArrayList { // If name and context is the same if(a.Name == name && a.Context == context) { // Add the amount to the existing account object in the array a.Amount += amount; // BUG! break; } else { // Add a new account object to the array Account newAccount = new Account(name, ns, context, amount); a1.Add(newAccount); // BUG! } }
There is an outer loop where name, context and amount are found. Hope I provided enough info. What is the right way of doing this?
You should be able to change the account itself - the first one
shouldn't be a problem, in other words (unless it's a value type?) -
but the second one is changing the list itself, which you can't do
without it throwing an exception. However, I'm surprised if you get a
*compiler* exception rather than a runtime exception.
Could you produce a short but complete example program which
demonstrates the problem?
--
Jon Skeet - <sk***@pobox.com> http://www.pobox.com/~skeet
If replying to the group, please do not mail me too
"Jon Skeet [C# MVP]" <sk***@pobox.com> wrote: You should be able to change the account itself - the first one shouldn't be a problem, in other words (unless it's a value type?) -
You're right. This is in fact no problem.
but the second one is changing the list itself, which you can't do without it throwing an exception. However, I'm surprised if you get a *compiler* exception rather than a runtime exception.
Rigth again. I learned to separate them now.
So, the problem remaining is how to add another Account within that loop.
The logic is:
1. See if the account already exists in the array.
2. If it does, add a new amount to the old one. If not, create a new account
in the array.
I'll see if I can come up with a simple example to work on.
Gustaf
Gustaf Liljegren <gu**************@bredband.net> wrote:
<snip> So, the problem remaining is how to add another Account within that loop. The logic is:
1. See if the account already exists in the array. 2. If it does, add a new amount to the old one. If not, create a new account in the array.
I'll see if I can come up with a simple example to work on.
You can't change a list while you're iterating through it. One common
solution is to build up another list containing the items you *want* to
add to the list, and then add all of them after you've finished
iterating. (You could use ArrayList.AddRange for that.)
--
Jon Skeet - <sk***@pobox.com> http://www.pobox.com/~skeet
If replying to the group, please do not mail me too
"Gustaf Liljegren" <gu**************@bredband.net> wrote in message
news:et**************@TK2MSFTNGP10.phx.gbl... So, the problem remaining is how to add another Account within that loop. The logic is:
1. See if the account already exists in the array. 2. If it does, add a new amount to the old one. If not, create a new
account in the array.
You could change the foreach-statement into a for-loop (going backwards).
Or even better. Not use an ArrayList, but a HashTable for the lookup.
Best Regards
- Michael S
"Jon Skeet [C# MVP]" <sk***@pobox.com> wrote: You can't change a list while you're iterating through it. One common solution is to build up another list containing the items you *want* to add to the list, and then add all of them after you've finished iterating. (You could use ArrayList.AddRange for that.)
Thanks for all your help. I see that I have not given a good enough
description. It's a grouping problem. The input data is a list of accounts
(identified by name) where some accounts occurs more than once. I want the
accounts grouped so that the amounts are summed up. For example, this input
data
Account 1: 2.50
Account 2: 7.00
Account 1: 1.50
Account 3: 9.00
Account 2: 3.50
Account 2: 6.00
Account 3: 3.50
Account 1: 6.50
shall result in these groups (each in an Account object):
Account 1: 10.5
Account 2: 16.5
Account 3: 12.5
My way of doing this is looping through the input data, account by account.
If the account has already been found, I just add the amount from the
current account object. If not, I add the whole object to the array. But it
won't work, since I can't add items to the array while iterating through it.
Maybe I need an Accounts collection class with methods like AccountExists(),
AddAccount() and UpdateAmount().
Gustaf
Gustaf Liljegren <gu**************@bredband.net> wrote: You can't change a list while you're iterating through it. One common solution is to build up another list containing the items you *want* to add to the list, and then add all of them after you've finished iterating. (You could use ArrayList.AddRange for that.)
Thanks for all your help. I see that I have not given a good enough description. It's a grouping problem. The input data is a list of accounts (identified by name) where some accounts occurs more than once. I want the accounts grouped so that the amounts are summed up. For example, this input data
Account 1: 2.50 Account 2: 7.00 Account 1: 1.50 Account 3: 9.00 Account 2: 3.50 Account 2: 6.00 Account 3: 3.50 Account 1: 6.50
shall result in these groups (each in an Account object):
Account 1: 10.5 Account 2: 16.5 Account 3: 12.5
My way of doing this is looping through the input data, account by account. If the account has already been found, I just add the amount from the current account object. If not, I add the whole object to the array. But it won't work, since I can't add items to the array while iterating through it.
It sounds like you should actually have two different lists (or rather,
a list and a map) - one for the input, and one for the output.
Something like (untested code)
foreach (Account account in inputList)
{
if (outputMap.ContainsKey(account.Name))
{
((Account)outputMap[account.Name]).Amount += account.Amount;
}
else
{
Account copy = new Account (account.Name, account.Amount);
outputMap[copy.Name]=copy;
}
}
--
Jon Skeet - <sk***@pobox.com> http://www.pobox.com/~skeet
If replying to the group, please do not mail me too This thread has been closed and replies have been disabled. Please start a new discussion. Similar topics |
by: matthurne |
last post by:
I need to send just an array to a function which then needs to go
through each element in the array. I tried using sizeof(array) /
sizeof(array) but since the array is passed into the function,...
|
by: s99999999s2003 |
last post by:
hi
I wish to pop/del some items out of dictionary while iterating over it.
a = { 'a':1, 'b':2 }
for k, v in a.iteritems():
if v==2:
del a
the output say RuntimeError: dictionary changed size...
|
by: Charles Sullivan |
last post by:
I'm working on a program which has a "tree" of command line arguments,
i.e.,
myprogram level1 ]]
such that there can be more than one level2 argument for each level1
argument and more than one...
|
by: Joe Rattz |
last post by:
Hmmm, I wrote the following code. I want an array of bools and I want to
intialize them to false.
bool bits = new bool;
foreach(bool bit in bits)
{
bit = false;
}
The compiler complains...
|
by: Yogi21 |
last post by:
Hi
I have a sorted array containing strings. I am iterating through the array and clearing the contents one by one using "array.BinarySearch" to find each element. So far so good. But the moment I...
| |
by: GiantCranesInDublin |
last post by:
Hi,
I am looking for the best performing solution for modifying and
iterating an object graph in JavaScript. I have outlined below a
simplified example of the object model and examples of how I...
|
by: pbali |
last post by:
Hi,
I am using PHP 5.1 and MySQL. I have a result set obtained by executing
PDO:: query. I want to create an XML file by using this result set. The
XML file will contain column names as XML node...
|
by: Mukesh |
last post by:
Hi,
I am using framework 2.0. I am writing a foreach loop that will
extract single dimensional arrays out of double dimensional array. I
am trying writing something like this.
string ...
|
by: raylopez99 |
last post by:
I would like to know if there's a quick "Linq" way to find the index
of an array having a particular value. I can do this the long way by
sequential iteration, but would like to know if there's a...
|
by: Hystou |
last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can...
|
by: Oralloy |
last post by:
Hello folks,
I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>".
The problem is that using the GNU compilers,...
| |
by: tracyyun |
last post by:
Dear forum friends,
With the development of smart home technology, a variety of wireless communication protocols have appeared on the market, such as Zigbee, Z-Wave, Wi-Fi, Bluetooth, etc. Each...
|
by: agi2029 |
last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing,...
|
by: isladogs |
last post by:
The next Access Europe User Group meeting will be on Wednesday 1 May 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM).
In this session, we are pleased to welcome a new...
|
by: TSSRALBI |
last post by:
Hello
I'm a network technician in training and I need your help.
I am currently learning how to create and manage the different types of VPNs and I have a question about LAN-to-LAN VPNs.
The...
|
by: adsilva |
last post by:
A Windows Forms form does not have the event Unload, like VB6. What one acts like?
|
by: 6302768590 |
last post by:
Hai team
i want code for transfer the data from one system to another through IP address by using C# our system has to for every 5mins then we have to update the data what the data is updated ...
| |
by: bsmnconsultancy |
last post by:
In today's digital era, a well-designed website is crucial for businesses looking to succeed. Whether you're a small business owner or a large corporation in Toronto, having a strong online presence...
| |