473,721 Members | 2,234 Online
Bytes | Software Development & Data Engineering Community
+ Post

Home Posts Topics Members FAQ

How do you modify an array while iterating through it?

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(newAccou nt); // 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

Nov 15 '05 #1
6 6053
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(newAccou nt); // 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.co m>
http://www.pobox.com/~skeet
If replying to the group, please do not mail me too
Nov 15 '05 #2
"Jon Skeet [C# MVP]" <sk***@pobox.co m> 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

Nov 15 '05 #3
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.AddRa nge for that.)

--
Jon Skeet - <sk***@pobox.co m>
http://www.pobox.com/~skeet
If replying to the group, please do not mail me too
Nov 15 '05 #4

"Gustaf Liljegren" <gu************ **@bredband.net > wrote in message
news:et******** ******@TK2MSFTN GP10.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
Nov 15 '05 #5
"Jon Skeet [C# MVP]" <sk***@pobox.co m> 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.AddRa nge 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

Nov 15 '05 #6
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.AddRa nge 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.Cont ainsKey(account .Name))
{
((Account)outpu tMap[account.Name]).Amount += account.Amount;
}
else
{
Account copy = new Account (account.Name, account.Amount) ;
outputMap[copy.Name]=copy;
}
}

--
Jon Skeet - <sk***@pobox.co m>
http://www.pobox.com/~skeet
If replying to the group, please do not mail me too
Nov 15 '05 #7

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

9
10702
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, sizeof(array) is really sizeof(pointer to first element in array) and therefore doesn't solve my problem. If I can't calculate the size of the array, can I go through the elements without knowing the size and somehow test whether I'm off the end...
5
8798
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 during iteration how can i suppress this message in an actual script and still get the final value of the dict?
28
12589
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 level3 argument for each level2 argument, etc. Suppose I code it similar to this fragment: int main( int argc, char *argv ) {
32
6515
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 on the "bit = false;" stating that bit is read-only.
2
1505
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 come to the last element, the BinarySearch method fails.It gives me a return value which is negative although the element is very much there. I am debugging through the code and I find nothing wrong with it.Note that i am using the first overloaded...
9
6301
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 will be using this graph. Object model:
3
2745
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 name and column values as node values. $orders = $db->query($sql); if (!empty($orders)) {
5
3640
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 strDetails foreach(string str in strDetails) { //Code comes here }
4
9984
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 shortcut. Specifically, you have an Array, say an array of Ints. You have a maximum value, i.e. int someValue = Array.Max(); and you would like to know which ith cell of the Array holds this value. How to do this without iterating the entire...
0
8730
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 effortlessly switch the default language on Windows 10 without reinstalling. I'll walk you through it. First, let's disable language synchronization. With a Microsoft account, language settings sync across devices. To prevent any complications,...
0
9367
Oralloy
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, it seems that the internal comparison operator "<=>" tries to promote arguments from unsigned to signed. This is as boiled down as I can make it. Here is my compilation command: g++-12 -std=c++20 -Wnarrowing bit_field.cpp Here is the code in...
1
9131
by: Hystou | last post by:
Overview: Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows Update option using the Control Panel or Settings app; it automatically checks for updates and installs any it finds, whether you like it or not. For most users, this new feature is actually very convenient. If you want to control the update process,...
0
9064
tracyyun
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 protocol has its own unique characteristics and advantages, but as a user who is planning to build a smart home system, I am a bit confused by the choice of these technologies. I'm particularly interested in Zigbee because I've heard it does some...
0
8007
agi2029
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, and deployment—without human intervention. Imagine an AI that can take a project description, break it down, write the code, debug it, and then launch it, all on its own.... Now, this would greatly impact the work of software developers. The idea...
0
5981
by: conductexam | last post by:
I have .net C# application in which I am extracting data from word file and save it in database particularly. To store word all data as it is I am converting the whole word file firstly in HTML and then checking html paragraph one by one. At the time of converting from word file to html my equations which are in the word document file was convert into image. Globals.ThisAddIn.Application.ActiveDocument.Select();...
0
4484
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 last exercise I practiced was to create a LAN-to-LAN VPN between two Pfsense firewalls, by using IPSEC protocols. I succeeded, with both firewalls in the same network. But I'm wondering if it's possible to do the same thing, with 2 Pfsense firewalls...
2
2576
muto222
by: muto222 | last post by:
How can i add a mobile payment intergratation into php mysql website.
3
2130
bsmnconsultancy
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 can significantly impact your brand's success. BSMN Consultancy, a leader in Website Development in Toronto offers valuable insights into creating effective websites that not only look great but also perform exceptionally well. In this comprehensive...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.