13

I just wondered why this ForEach doesn't work and leaves the values with trailing whitespace.

string days = "Monday, Tuesday, Wednesday, Thursday, Friday";

string[] m_days = days.Split(',');

m_days.ToList().ForEach(d => { d = d.Trim(); } );

I know there are other ways of doing this so i don't need and answer there.

4 Answers 4

28

Because you are not reassigning the trimmed strings.

var list = m_days.Split(',').Select(s => s.Trim()).ToList();

Why ForEach doesn't work or if I am using the ForEach incorrectly?

ForEach is not Linq, it's a method of List<T>. What you are doing is basically this:

foreach(string day in m_days)
{
    day.Trim();  // you are throwing away the new string returned by String.Trim
}

Instead of using LINQ you could also use a for-loop instead:

for(int i = 0; i < m_days.Length; i++)
{
    m_days[i] = m_days[i].Trim();
}
Sign up to request clarification or add additional context in comments.

4 Comments

yeh i want to know why ForEach doesn't work or if I am using the ForEach incorrectly. I know you can use a Select statement...
@David: Please see my answer for an explanation on why you can't use ForEach for this task.
@David: ForEach is not Linq, it's a method of List<T>. Edited my answer.
yeh, ignore that linq tag. means nothing to the question anyway
4

You need to assign the output of your ForEach to a new variable, like so:

var trimmedResult = m_days.Select(d => d.Trim()).ToList();

Comments

4

string.Trim returns a new string instance. So you have to somehow use that new instance.
You are not doing that in your code.
Furthermore, it is not possible with ForEach. At first glance, the following could work:

m_days.ToList().ForEach(d => { d = d.Trim(); });

But that isn't going to help you either, because d is not passed by reference, so you are only changing the local parameter that has been passed into your delegate and not the instance stored in the list.

You most likely want this:

var result = days.Split(',').Select(x => x.Trim()).ToList();

An alternate way without LINQ would look like this:

var split = days.Split(',');
for(int i = 0; i < split.Length; ++i)
    split[i] = split[i].Trim();

3 Comments

beat me to the post but this is the best solution imo
Ok, no need to post further alternatives. I know the alternatives. I think I may have been misunderstanding the use of the ForEach. I just wanted to know why exactly the Foreach doesn't work
@David: Well, that's explained in my answer in the part after the first code snippet.
3

Because String.Trim() do not modify original string. When you call ForEach(d => d.Trim()) you create new trimmed string in memory for each item of list, but that string is not assigned anywhere. Thats what you are doing:

foreach(string d in list)
{
    d.Trim();
}

What you need is

m_days = days.Split(',').Select(d => d.Trim()).ToArray();

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.