I'm currently investigating some problems with a list (or array, I'm using "list" in this post equally to an array because an array can be converted to a list when needed)
For example I have
List<Car> cars = new List<Cars>();
My Car object is made this way
public class Car
{
public double Weight {get; set;}
public double TopSpeed {get; set;}
public int NumberOfPassengers {get; set;}
public string ModelName {get; set;}
}
In the watch list I want to see the items of the list but only care about the ModelName property. Is there any way to show me the expanded list in the watch list and only show the ModelName property?
Currently when I expand the list It shows me that it contains 4 elements and in the Value column it only shows me (somename.namespace.Car). So I need to expand every element of the list further to see all properties but this is getting messy if the list gets longer or there are many elements in the list. One constraint --> the class Car is not under my control and therefore I can't overwrite its ToString() method or use [DebuggerDisplay()].
I tried using Linq ForEach(x => Console.write(x.modelName) but that is not working.
I'm happy about any advice or tip :-)
Thanks to #nilsK hint. I found this solution:
Simply using this watch expression:
myListWithCars.Select(x => x.modelName).ToList()
Related
Let's say I have a WriteItem class that looks like this:
public class WriteItem
{
public string Name { get; set; }
public object Value { get; set; }
public int ResultCode { get; set; }
public string ErrorMessage { get; set;}
}
I need to process each item and set its ResultCode and ErrorMessage properties and I though about defining a method similar to this:
public void ProcessItems(WriteItemCollection items)
{
foreach(var item in items)
{
// Process each item and set its result.
}
}
The processing of each item is done by another class.
Is this the best way to do it?
Or is it better to have the method return a collection of a custom Result class?
Both options have their advantages and disadvantages. Both are "fine" in the sense that there is nothing wrong with them and they are commonly used in C#.
Option 1 has the big advantage of being simple and easy. You can even keep a reference to a WriteItem instance and check its status after processing.
Option 2 has a clearer separation of concerns: In Option 1, you need to add comments to your WriteItem class to define which are "input" and which are "output" properties. Option 2 does not need that. In addition, Option 2 allows you to make WriteItem and ProcessingResult immutable, which is a nice property.
Option 2 is also more extensible: If you want to process something else than WriteItems (with the same return options), you can define a class
class ProcessingResult<T>
{
public T Item { get; set; }
public int ResultCode { get; set; }
public string ErrorMessage { get; set; }
}
and use it as ProcessingResult<WriteItem> as well as ProcessingResult<SomeOtherItem>.
What you wrote will work. You can modify the object properties without having side effects while iterating in the collection.
I wouldn't return a new collection unless you need to keep a copy of the original collection untouched.
I think it all comes down to readability.
When you call ProcessItems, is it obvious that the collection has changed? If you call the method like this:
var items = GetItemsFromSomewhere();
ProcessItems(items);
versus calling it like this:
var items = GetItemsFromSomewhere();
items = ProcessItems(items);
or simply changing your methodname:
var items = GetItemsFromSomewhere();
items = UpdateItemStatuses(items);
In the end there is no right answer to this question in my book. You should do what feels right for your application. And consider: what if another developer was looking at this piece of code? Can he surmise what is happening here, or would he have to dive into the ProcessItems-function to get the gist of the application.
It is better to return a new results class.
why?
As others have said you are modifying the collection and its not really clear. But for me this is not the main reason. You can have processes which modify objects.
For me its because you have had to add extra properties to your WriteItem object in order to support the processor. This in effect creates a strong coupling between the model and a processor which should not exist.
Consider you have another method ProcessItems_ForSomeOtherPurpose(List<WriteItem> items) do you expand your ResultCode int to have more meaningful values? do you add another property ResultCode_ForSomeOtherPurpose? what if you need to process the same item mutiple times with multiple processors?
I would give your Model an Id. Then you can log multiple processes against it
eg.
item 1 - loaded
item 1 - picking failed!
item 1 - picked
item 1 - delivered
I want to send details of 2 different models to the view so I do this with a view model.
namespace Apps.Models
{
public class viewmodel1
{
public App app { get; set; }
public List<Colleague> colleague { get; set; }
}
}
app being a model that stores a variety of properties about an application, and colleague being a model that stores a variety of properties about colleagues.
Originally I was only passing in app, but I want to be able to display a drop down list of the colleagues first names in this view when creating an app (because the two are linked) so i need to pass in all the current colleagues to get their first names. This part is working.
However, my action result needs to change when the form is submitted to take in this new viewmodel type, and I don't know how to access the properties from the action result. Normally when you bind include there are just properties in the model, but i want to include the properties that are WITHIN the objects the viewmodel has. I don't know how to do this or of i am just doing something wrong.
I would obviously like to retain the validation that is already written for the app properties, but I'm not sure I can do that this way.
Not sure if this is the answer to your question without seeing the xaml binding you are trying to use, but you can use bindings that dive into objects.
So if you have an Employee object that is your DataContext (Employee would be your ViewModel although it has no controller logic, so I guess it's just a model here):
public class Employee
{
public string Name {get; set;}
public EmpAddress Address {get; set;}
}
public class EmpAddress
{
public string Street {get; set;}
public string Zip {get; set;
}
You can do bindings that look like this:
<TextBlock Text={Binding Address.Street}/>
Let me know if this isn't what you were after and I'll try to help.
I need to create a list with more than 400 items and each item has 3 properties, in c#. Like:
Name
Profession
Age
Marital Status
The relevant detail is that, to access individual data, I do not want to loop over each Name with a foreach or something else, but I want to access the data directly.
Assuming I need data from a person called Ana_Salgado, which name is stored in a string called PersonName, would it be possible to access these data like: PersonName.Profession?
Any ideas? Thank you in advance :)
You can use Dictionary, in this way
Class Members
{
public string Profession {get; set;}
public string Age {get; set;}
public string MaritalStatus {get; set;}
}
Dictionary<string, Members> dict = new Dictionary<string, Members>();
In this way you have a data model where the name is the key of your dictionary, and
you can use dict["Ana_Salgado"].Age or any of Members property.
Use Dictionary instead of list for example. And then you would be able write something like myDictionary["Ana_Salgado"].Profession
I have a Model which consist of Employees information. In my model there is a property called City which define the city of Employee in which he lives. The propery is shown below
public string City{get;set;}
Now I have a view which contains a form which will be filled by a employee to register. I want to use a dropdownlist for selecting cities. I think the below code will be used for dropdown as i discovered. My model name is Employee.
#Html.DropDownListFor(m=>m.City,new SelectList())
Please tell me that "is there any way to define the options for dropdownlist in SelectList() method directly Like ... in html?"
If not, where should i define the class for this drop down, where to call and where to render.I don't know where to define values? I am very confused because this is mvc and we have to seperate concern and i think we cannot define anything at anywhere?
Thanks in advance..
You have at least two options:
1.) Add a list, array, or any other collection type of cities to your model
2.) Add a SelectList property to your model
Option 1 can be something as simple as an array of strings, or can be, say, an IEnumerable of City objects. You would then need to transform this property to a collection of SelectListItem objects in the view as part of the DropDownList binding.
Option 2 has the advantage of being capable of direct binding to the DropDownList, but requires that you construct the list within the action method.
Then end result is the same, it's just a matter of how pedantic you want to be about SoC.
For example (assuming you add a property called Cities):
#Html.DropDownListFor(m=>m.City, Model.Cities.Select(city => new SelectListItem()
{
Text = city,
Value = city,
Selected = city == Model.City
})
EDIT:
To answer your comment, I have to make some assumptions. I will assume you have a model called EmployeeModel. This model has a property, City, that is a plain string. So, this is a partial of your model, as I assume it to be:
public class EmployeeModel
{
public string City { get; set; }
// ... other properties ...
}
So, if you need to add a property for binding to your dropdown, you would do one of the following:
public class EmployeeModel
{
public string City { get; set; }
public IEnumerable<string> Cities { get; set; }
// ... other properties ...
}
or
public class EmployeeModel
{
public string City { get; set; }
public SelectList Cities { get; set; }
// ... other properties ...
}
This new property will contain the list of cities that you allow your user(s) to pick from.
If you choose the first option, you load the IEnumerable from your datastore, and then use the first example above in your view, which uses LINQ to project each string in the Cities property into a new SelectListItem object.
If you go with the second option, you build a SelectList in the action prior to passing the model to the view. This isn't terribly difficult, as the class provides a constructor that takes an IEnumerable (your list of cities) and the "selected value," which will be the City property (see http://msdn.microsoft.com/en-us/library/dd460123%28v=vs.108%29.aspx). Your code would look something like:
model.Cities = new SelectList(GetCities(), model.City);
This, of course, assumes you have a helper method (GetCities()) to load your cities from wherever they are stored. Your view then would have something like this:
#Html.DropDownListFor(m=>m.City, model.Cities)
The view engine then uses these SelectListItems to build the <select> element and it's <option> elements.
You could have this in your model, it's quickly achieved, although I wouldn't recommend it:
public class Place
{
public string City{get;set;}
public SelectListItem[] Cities()
{
return new SelectListItem[2] { new SelectListItem() { Text = "London" }, new SelectListItem() { Text = "New York" } };
}
}
...and your view
#Html.DropDownListFor(m => m.City, Model.Cities())
I think the best place for something like this (but is a little more complicated) is your own htmlhelper and usage could look something like:
#html.CityDropDownFor(m => m.City)
You could cache the cities nicely and it keeps data and UI work out of your models.
If you want to learn more about creating your own helpers, I'd suggest a bit of a [read up].1
i wan to create a linked list that contains the name , age and address of some people , so far i created that code :
LinkedList<string> details = new LinkedList<string>();
details.AddFirst("Name1");
details.AddLast("Name2");
details.AddLast("Name3");
foreach (var display in details)
{
Console.WriteLine(display);
}
ok so now it works fine , but i just input the name , how can i input the age and address , is it like array ? i just don`t know much about linkedlists , and also i tried to delete some nodes of the linkedlist but i failed :
foreach (var item in details)
{
if (item.Contains("Name3"))
{
details.Remove(item);
}
}
but i get that error :
Unhandled Exception: System.InvalidOperationException: Collection was modified after the enumerator was instantiated.
and finally , how can i edit a linkedlist item , like renaming Name2 to Name13 or anything , i would really appreciate any help , just give me idea and i`ll continue digging . Thanks in advance .
You can't remove elements from the list while iterating a list using foreach loop.
if (details.Remove("Name3"))
Console.WriteLine("Removed");
else
Console.WriteLine("Not Found");
A linked list is like an array in that it is a collection of data. Each item in the list stores a link to the next item (and often the previous), hence the name.
You can't modify a list you're looping over, because your reference into the list will then be invalid.
If you wish to add extra information within the list, simply create a class which encapsulates that information, as the LinkedList is a generic type. For example:
//Structure to hold extra information
public class PersonDetails
{
public string Name {get; private set;}
public int Age {get; private set;}
public string Address {get; private set;}
//Constructor
public PersonDetails(string name, int age, string address)
{
this.Name = name;
this.Age = age;
this.Address = address;
}
}
Then you can create a new linked list containing those types:
LinkedList<PersonDetails> list = new LinkedList<PersonDetails>();
list.AddFirst(new PersonDetails("Name", 22, "Address"));
Note that you cannot modify a collection when you are enumerating it, you need to perform your check and modify it outside of your foreach loop.
If you can use LINQ, you can convert your code to a linq approach such as:
details = details.Where(item => !item.Contains("Name3")).ToList();