c# list in property which is array - c#

This is my property class:
class Actions
{
public string[] Style { get; set; }
}
and this is my main method:
Actions action = new Actions();
List<string> list = new List<string>();
list.Add("one");
list.Add("two");
foreach (var item in list)
{
for (int i = 0; i < action.Style.Length; i++)
{
action.Style[i] = item.ToString();
Console.WriteLine(action.Style[i]);
}
}
How do I fill the property with list items?
This gives me a exception:
"object reference not set to an instance of an object".

There is no need to add your items one by one, you could just use the ToArray() method of your list like so:
List<string> list = new List<string>();
list.Add("one");
list.Add("two");
Actions action = new Actions {
Style = list.ToArray()
};

As has already been pointed out, Style is always null, given the code you have shared. #Eldeniz and #paul have shared different ways to fix that. Obviously, your sample code is just a sample fragment, so here are 2 other options you could consider if the previous two don't work for whatever reason (I'm just free-handing this, please excuse any typos).
1) You can have your Actions class always return a not-null object
class Actions
{
private string[] _style;
public string[] Style
{
get { return _style ?? new string[0]; }
set { _style = value; }
}
}
Note that this will allow you to always see the output of the style property as requested, assuming an empty array and null are, for your purposes, the same thing.
2) You can make your loop tolerant to null values
foreach (var item in list)
{
for (int i = 0; i < action?.Style.Length ?? 0; i++)
{
action.Style[i] = item.ToString();
Console.WriteLine(action.Style[i]);
}
}
Finally, just as a tip, if you have your debugger attached and you are stepping through your code, Visual Studio will help you pinpoint these sorts of errors pretty easily. Take the time to become friends with your debugger. If it gives you an error you don't understand, do a quick web search. Your future self will thank you.

You must create an instance of the Style property
List<string> list = new List<string>();
list.Add("one");
list.Add("two");
Actions action = new Actions();
action.Style=new string[list.Count];
foreach (var item in list)
{
for (int i = 0; i < action.Style.Length; i++)
{
action.Style[i] = item.ToString();
Console.WriteLine(action.Style[i]);
}
}

Related

MVC List Error List<Model>

I'm using foreach to transfer data from list to another but when adding value updated automatically to last value added. For example:
list1 = [1,2,3]
list2 = new List<Model>()
foreach(var item in list1) {
list2.Add(item)
}
the result in list2 is [ 3, 3, 3]
Actually example is below :
var _sizes = new List<ProductsSize>();
var _size = new ProductsSize();
if (model.Dynamic_ProductsSize.Count > 0)
{
foreach (var item in model.Dynamic_ProductsSize)
{
_size.SizeId = item;
_sizes.Add(_size);
}
}
model.ProductsSize = _sizes.ToList();
I need to know why it only takes the last item and what is the solution for this case
You only have one ProductsSize object:
var _size = new ProductsSize();
And you keep modifying that same object. All references to that object, including any list elements it's been added to, get updated when you modify that one object.
Instead, create your new object in the loop:
foreach (var item in model.Dynamic_ProductsSize)
{
var _size = new ProductsSize();
_size.SizeId = item;
_sizes.Add(_size);
}
That way each element in the list is a new object instead of the same object added multiple times.
Side note, you have a few things in the code which aren't necessary. Checking the length before the loop, for example, as well as converting a list to a list at the end.
In fact, I imagine all of the code shown can be shortened to simply this:
model.ProductsSize = model.Dynamic_ProductsSize.Select(p => new ProductsSize { SizeId = p }).ToList();
In which case you're also just converting one model property to another model property. Why not put this logic in the model itself and skip the whole thing?
public IEnumerable<ProductsSize> ProductsSize
{
get { return this.Dynamic_ProductsSize.Select(p => new ProductsSize { SizeId = p });
}
Unless there's a particular reason you want the same data twice in two different properties that isn't clear from this code, having one set of data and just different views/calculations/etc. of that data is often preferred.
Create a new object before adding it to the list. You can use the object initializer syntax to keep it concise:
if (model.Dynamic_ProductsSize.Count > 0)
{
foreach (var item in model.Dynamic_ProductsSize)
{
_sizes.Add(new ProductsSize(){SizeId = item});
}
}

Pass array of anonymous classes to method and loop c#

I'm a newbie in c# and would like to ask you something, please help.
I created a variable with 3 persons inside using anonymous classes like this:
var personas = new[] {
new {nombre = "Guillermo", apellido = "Pérez", edad = 37}
, new {nombre = "Juan", apellido = "García", edad = 27}
, new {nombre = "Maria", apellido = "Rosina", edad = 47}
};
Now, I tried to iterate on each of these items and I did (using the following code)
for (int i = 0; i < personas.Length; i++)
{
var persona = personas[i];
Console.WriteLine("{0} {1} tiene {2} años.", persona.nombre, persona.apellido, persona.edad);
}
THE PROBLEM comes when I want to create a method to do what I did with the last piece of code, the idea is to create a method and pass this object (in this case personas) to the method and do the loop inside. What I did is this:
showPersonas(personas);
static void showPersonas(object[] personsList) {
for (int i = 0; i < personsList.Length; i++) {
var algo = personsList[i];
Console.WriteLine(personsList[i].nombre); ----> ERROR!!
}
}
What I would like the method to do is to do what I did with the for loop, to be able to receive the object, iterate and print each item.
THANK YOU! for all your attention.
I see two options
Best option on my opinion is creating class Person. With created type compiler will show error during compiling time if you make typo while writing property name of will try to rename it later.
public class Person
{
public string Nombre { get: set; }
public string Apellido { get: set; }
public string Edad { get: set; }
}
static void showPersonas(Person[] personsList)
{
foreach (var algo in personsList)
{
Console.WriteLine(algo.nombre);
}
}
Another option: dynamic keyword.
But be careful - with dynamic keyword you move type checking to the runtime. Which will throw same exception, which you now getting in compile time, during runtime.
static void showPersonas(dynamic[] personsList)
{
for (int i = 0; i < personsList.Length; i++)
{
var algo = personsList[i];
Console.WriteLine(algo.nombre);
}
}
As for the answer you can do it like this:
static void showPersonas(dynamic[] personsList){
for (int i = 0; i < personsList.Length; i++){
var algo = personsList[i];
Console.WriteLine(personsList[i].nombre);
}
}
Be aware what dynamic will throw exceptions if field not presented in your objects.
As for the BEST way to do this, just create class for this object and use it. You see, C# is not designed as javascript or python and should not be ever used like one.
It is strong typed language and in my opinion this is advantage.

How to display data of collection(object collection)

I have made a collection to store objects of class sendviaemail
public List<SendViaEmail> email = new List<SendViaEmail>();
The class has a string variable to store emailid. I am adding one object to the list email.
email.Add(s);
Now the s object is of class type email and it contains an emailed(For eg sad#gmail.com)
When I use foreach loop to iterate through all the values in object and add all the emailids in listbox but no data is displayed in listbox
SendViaEmail s = new SendViaEmail();
for (int i = 0; i < s.email.Count(); i++)
{
listBox1.Items.Add(s.email);
}
I tried debugging and in the s object the email = null .
I don't think the code to store email address in the collection works because I m getting null value when I retrieve data.
I m having the email address in string.
How to store string in collection which can hold only objects of class
Firstly, you should be using a Typed List.
That means the List can only contain elements of the SendViaEmail object.
public List<SendViaEmail> email = new List<SendViaEmail>();
You can then add SendViaEmail objects to it.
SendViaEmail s = new SendViaEmail();
email.add(s);
Your loop structure can now take advantage of foreach:
foreach(SendViaEmail s in email){
listBox1.Items.Add(s.email);
}
Try setting the DisplayMember property of listBox1 to "" and then "email".
listBox1.DisplayMember = "";
listBox1.DisplayMember = "email";
This should refresh the view.
Use a foreach loop rather than a for.
foreach (string email in s.email)
{
listBox1.Items.Add(email);
}
If you want to use a for loop, you need to use the index to get the current item.
for (int i = 0; i < s.email.Count(); i++)
{
listBox1.Items.Add(s.email[i]);
}
You are adding the list multiple times, instead of adding each of its element.
This is what you are supposed to do :
SendViaEmail s = new SendViaEmail();
for (int i = 0; i < s.email.Count(); i++)
{
listBox1.Items.Add(s.email[i]);
}
Alternatively, you could use foreach as well :
SendViaEmail s = new SendViaEmail();
foreach (var item in s.email)
{
listBox1.Items.Add(item);
}

C# Converting List to 2d list and adding additional values

Hello need some assistance with this issue. Hopefully i can describe it well.
I have a parser that goes though a document and find sessionID's, strips some tags from them and places them into a list.
while ((line = sr.ReadLine()) != null)
{
Match sID = sessionId.Match(line);
if (sID.Success)
{
String sIDString;
String sid = sID.ToString();
sIDString = Regex.Replace(sid, "<[^>]+>", string.Empty);
sessionIDList.Add(sIDString);
}
}
Then I go thought list and get the distinctSessionID's.
List<String> distinctSessionID = sessionIDList.Distinct().ToList();
Now I need to go thought he document again and add the lines that match the sessionID and add them to the list. This is the part that I am having issue with.
Do I need to create a 2d list so I can add the matching log lines to the corresponding sessionids.
I was looking at this but cannot seem to figure out a way that I could copy over my Distinct list then add the Lines I need into the new array.
From what I can test it looks like this would add the value into the masterlist
List<List<string>> masterLists = new List<List<string>>();
Foreach (string value in distinctSessionID)
{
masterLists[0].Add(value);
}
How do I add Lines I need to the corresponding Masterlist. Say masterList[0].Add value is 1, how do i add the lines to 1?
masterList[0][0].add(myLInes);
Basically i want
Sessionid1
-------> related log line
-------> Related log line
SessionID2
-------> related log line
-------> related log line.
So on and so forth. I have the parsing all working, it's just getting the values into a 2nd string list is the issue.
Thanks,
What you can do is, simple create a class with public properties, and make list of that custom class.
public class Session
{
public int SessionId{get;set;}
public List<string> SessionLog{get;set;}
}
List<Session> objList = new List<Session>();
var session1 = new Session();
session1.SessionId = 1;
session1.SessionLog.Add("description lline1");
objList.Add(session1);
Here is one way to do it:
public class MultiDimDictList: Dictionary<string, List<int>> { }
MultiDimDictList myDictList = new MultiDimDictList ();
Foreach (string value in distinctSessionID)
{
myDictList.Add(value, new List<int>());
for(int j=0; j < lengthofLines; j++)
{
myDictList[value].Add(myLine);
}
}
You would need to replace lengthofLines with a number to indicate how many iterations of lines you have.
See Charles Bretana's answer here

C# Removing a List from a List

Is there a convenient way to remove a nested list from another list if it meets certain requirements? For example, say we have a collection of stops, and we decide to call each collection of stops a route. Each route is in list from. Then we decide to put each route into a list as well.
So now that we have a list of routes, someone decides that certain types of routes really shouldn't be included in the route list. How can I remove those routes? Here's some sample code:
Example Class
public class Stops
{
public Stops(int _param1, string _param2)
{
param1 = _param1;
param2 = _param2;
}
public int param1 { get; set; }
public string param2 { get; set; }
}
Create the Lists
List<List<Stops>> lstRoutes = new List<List<Stops>>();
List<Stops> lstStops = new List<Stops>();
List<Stops> lstMoreStops = new List<Stops>();
// Create some stops
for (int i = 0; i < 5; i++)
{
lstStops.Add(new Stops(i, "some text"));
}
lstRoutes.Add(lstStops);
// Create some more stops
for (int i = 5; i < 10; i++)
{
lstMoreStops.Add(new Stops(i, "some more text"));
}
lstRoutes.Add(lstMoreStops);
How can I remove any route from lstRoutes that has, say, any param1 value greater than 6?
The simplest way (which can be applicable to all enumerables, not just lists) would be:
lstRoutes = lstRoutes.Where(r => !r.Any(s => s.param1 > 6)).ToList();
The snippet above creates a new list, so copying will occur which means both the performance and memory usage will slightly suffer. The most efficient way would be not adding those items to the list in the first place.
The second most efficient way would be to remove items from the list instead of constructing a new one, so the memory usage wouldn't be affected as much:
lstRoutes.RemoveAll(r => r.Any(s => s.param1 > 6));
List<Stops> stop = lstRoutes.Find(delegate(List<Stops> stp) { return stp.param1 > 6; });

Categories

Resources