4

I have a model Person (with among other fields the day of Birth) and I want to pass a list of all persons, together with the calculated age of each person, to the view

Therefor:

  1. The view model

    public class vm_PersonList
    {
        public Person Person { get; set; } 
        public int age { get; set; }
    }
    
  2. The controller action:

    public ActionResult PersonList()
    {
        ViewBag.Message = "My List";
    
        var list = new List<vm_PersonList>();
        var list_p = new vm_PersonList();
    
    
        foreach (var p in db.Person)
        {
            list_p.Person = p;
            //the age will be calculated based on p.birthDay, not relevant for the    
            //current question
            list_p.age = 23;
    
            list.Add(list_p);
        }
        return View(list);
    }
    
  3. The view

    @model List<programname.Viewmodels.vm_PersonList>
    
    @foreach (var p in Model)
    {
        <tr>
            <td>
                @p.Person.FullName
            </td>
            <td>
                @p.age
            </td>  
        </tr>
    }
    

The Person table contains for example 6 entries. When debugging the application I see:

At the end of the controller action "list" contains correctly the 6 different Person entries

In the view, the "Model" contains 6 entries, but 6 times the last "database entry". Does anyone have a suggestion to solve this issue?

1
  • move var list_p = new vm_PersonList(); into the foreach loop. Commented May 25, 2012 at 8:07

3 Answers 3

7

You are using the same list_p instance over and over again inside the loop. So you are constantly updating its Person property. And since Person is a reference type you are modifying the same reference in memory. At the last iteration of the loop you are obviously replacing this reference with the last instance of Person which explains why you are seeing the same person in the view.

Try like this, seems lot easier:

public ActionResult PersonList()
{
    ViewBag.Message = "My List";
    var model = db.Person.Select(p => new vm_PersonList
    {
        Person = p,
        age = 23
    }).ToList();
    return View(model);
}
Sign up to request clarification or add additional context in comments.

Comments

1

You are working on the same instance of vm_PersonList. Move the instantiation of vm_PersonList into the loop

foreach (var p in db.Person)
{
    var list_p = new vm_PersonList();
    list_p.Person = p;
    //the age will be calculated based on p.birthDay, not relevant for the    
    //current question
    list_p.age = 23;

    list.Add(list_p);
}

Comments

0

It's an issue with the scope of your list_p instance. Try changing your controller code to:

public ActionResult PersonList()
{
    ViewBag.Message = "My List";

    var list = db.Person
        .Select(p => new vm_PersonList
                     {
                         Person = p,
                         age = 23,
                     })
        .ToList();

    return View(list);
}

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.