how can i to add items to an already created Array - c#

i have string array as the following
string[] strArray = new string[] { "1", "2", "3", "5", "6" };
the question is
how can i add item to this created Array at specific position
to be like
{ "1", "2", "3" , "4" , "5", "6" }
i need some thing can append value at specific index and keep the old values

You can't do this, since arrays have fixed length after creation. Use List<string> instead (which internally stores its items in array):
var strList = new List<string> { "1", "2", "3", "5", "6" };
strList.Insert(2, "foo");
If you'll need to convert the list into array, use ToArray extension method:
var strArray = strList.ToArray();

Arrays are immutable, but Lists are not:
var list = strArray.ToList();
list.Add("6")
strArray = list.ToArray();
Or, at a specific index:
var list = strArray.ToList();
list.Insert(3, "4");
strArray = list.ToArray();

Related

LINQ SequenceEqual returns false but comparing using Except gives different result

I have two lists that I believe to be equal and in same sequence, but when I run SequenceEqual() it is returning false. See below for pseudo example:
// For brevity’s sake assume the two-list data is as follows
List<string> list1 = new List<string> {"1", "2", "3"};
List<string> list2 = new List<string> {"1", "2", "3"};
list1.SequenceEqual(list2); // returning false
list1.Except(list2).Count(); // returning 0
list2.Except(list1).Count(); // returning 0
In reality my list data is much larger (~ 8000 items), but I am confused why I would get 0 for both Except().Count() yet false for SequenceEqual()?
Edit: Added Count to the Except examples.
You do different comparisons. As for Except it
Removes duplicates
Doesn't take order of items into account
Ignores items which are in the second argument if they are not present in the first
that's why
// Duplicated "2" will be ignored
List<string> list1 = new List<string>() { "1", "2", "3", "2" };
// Duplicated "3" will be ignored
// Order doesn't matter
// "7777777" will be ignored
List<string> list2 = new List<string>() { "3", "3", "1", "2", "7777777"};
// 0; since all items within list1 - "1", "2", "3"
// are in the list2, duplicates ignored
int count = list1.Except(list2).Count();
When SequenceEqual returns true if and only if sequences are equal order and duplicates matter. In the example above SequenceEqual returns false since list1.Count != list2.Count, list1[0] != list2[0] etc.

Modifying source items changes list items? [duplicate]

This question already has answers here:
Issue with List.Add() only saving the last added item [duplicate]
(2 answers)
Closed 4 years ago.
I'm coding a little plugin for a software using Windows Forms in C#.
I need to parse an XML file to retrieve some objects and add them into a ListBox. The problem is that at the end of my program, all objects are the same as the last one added.
I kind of figured out why, but I'm still searching how to resolve it. Here is a little example with a String[] instead of my objects:
static void Main(string[] args)
{
ListBox listbox = new ListBox();
String[] s = new string[] { "5", "2", "3" };
listbox.Items.Add(s);
s[2] = "0";
listbox.Items.Add(s);
Console.WriteLine(((String[])listbox.Items[0])[2]); // result => 0
Console.WriteLine(((String[])listbox.Items[1])[2]); // result => 0
Console.ReadLine();
}
ListBoxes use pointers, updating the value in the first array you are updating the value of the pointer labled "s", in order to use the same value name but different arrays you have to clone the starting array
ListBox listbox = new ListBox();
String[] s = new string[] { "5", "2", "3" };
listbox.Items.Add(s);
s = (String[])s.Clone();
s[2] = "0";
listbox.Items.Add(s);
Console.WriteLine(((String[])listbox.Items[0])[2]); // result => 3
Console.WriteLine(((String[])listbox.Items[1])[2]); // result => 0
Console.ReadLine();
With listbox.Items.Add(s); you are adding only one item being the array itself. Use AddRange instead to add the elements of the array.
listbox.Items.AddRange(s);
Another way to make it work is to set the DataSource:
listbox.DataSource = s;
Let's see what happens in your codeh in detail (with line numbers)
1 String[] s = new string[] { "5", "2", "3" };
2 listbox.Items.Add(s);
3 s[2] = "0";
4 listbox.Items.Add(s);
An array is created and initialized.
This array is added as one single item to the ListBox. Note that the array is a reference type. So indeed, you are only adding a reference to the ListBox, not a copy of the array.
One element of the array is changed. This affects the first item added to the ListBox as well, since it contains a reference to this unique array.
The same array-reference is added as an item to the ListBox. Now the ListBox contains 2 items referencing the same array with the same elements.
If you want the items to contain 2 distinct arrays, you can clone the array:
string[] s = new string[] { "5", "2", "3" };
listbox.Items.Add(s);
var s2 = (string[])s.Clone();
s2[2] = "0";
listbox.Items.Add(s2);
Now you have two distinct items in the ListBox. Note that the Array.Clone Method creates a shallow clone. I.e. the array elements themselves are not cloned. So, if they are reference types, both arrays will contain the same objects just after cloning. But since you have 2 distinct arrays, you can replace elements of an array without affecting the other array.
You can add a clone method to your own classes
public class MyOwnClass
{
public string Prop1 { get; set; }
public int Prop2 { get; set; }
public MyOwnClass ShallowClone()
{
return (MyOwnClass)MemberwiseClone();
}
}
MemberwiseClone is inherited from System.Object.
It is showing the last updated values because string are of reference types which will replace the all existing references on update. So you need create new array and then add to the list box as source.
static void Main(string[] args)
{
ListBox listbox = new ListBox();
String[] s = new string[] { "5", "2", "3" };
listbox.Items.Add(s);
String[] s2 = new string[] { "5", "2", "0" };
listbox.Items.Add(s2);
Console.WriteLine(((String[])listbox.Items[0])[2]); // result => 0
Console.WriteLine(((String[])listbox.Items[1])[2]); // result => 0
Console.ReadLine();
}

Convert JSON [][] to object in c#

I have a little problem converting my JSON Object I have to something I can work within C# code.
{ "CheckboxHours": {
"method": "ID",
"valueparts": [
"Hour",
[ "0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "10", "11", "12", "13", "14", "15", "16", "17", "18", "19", "20", "21", "22", "23" ]
]
}
}
This is my JSON String I have, which is for creates me the Selenium Object.
What i want is to combine the values from valueparts[0] ("Hour") with valueparts[1][0-23] with each other and create an array of Selenium Objects
var jsonData = JsonConvert.DeserializeObject<jsonc#file>(_jsonFile);
Object[] hours = (Object[])jsonData.CheckboxHours.Valueparts[1];
SeleniumCheckBox[] checkbox = new SeleniumCheckBox[hours.Length];
for (int i = 0; i < hours.Length; ++i)
{
cbHour[i] = new SeleniumCheckBox(jsonData.CheckboxHours.Valueparts[0].ToString() + hours[i]);
}
The SeleniumCheckBox is a Class I made which just takes the value and creates in the background a new Selenium Element with findElement(By.ID(value)). This is working already.
My Problem here is that he doesn't allow the Conversion from jsonData to Object[] and I don't really know how I can handle this.
I hope it is clear what I want to have - if not feel free to ask for more specific data.
I think. You can try this.
var jsonData = JsonConvert.DeserializeObject<dynamic>(_jsonFile);
var hours = jsonData.CheckboxHours.valueparts[1];
foreach (var hour in hours)
{
//Some code
}
I am not sure if I understood everything correctly, but the reason for failure in deserialization might be that valueparts is List parameter, usually in c# the Lists contain only 1 type of parameters eg. string, or int. In your case, "Hour" (valueparts[0]) is a string, and valueparts[1] is List. I assume here is the conflict with deserializing the JSON string.
{
CheckboxHours:{
"method":"ID",
"valueparts":{
Measure: "Hour",
MesureValues:
[
"0","1","2","3","4","5","6","7",
"8","9","10","11","12","13","14",
"15","16","17","18","19","20",
"21","22","23"
]
}
}
}
Change valueparts to object, as in the code above, so you can use Hour as string and the values as List.

Getting common values in two array issue using LINQ

I have two arrays say
var list1 = string[] {"1", "2", "3", "4", "", ""};
var list2 = string[] {"2", "3", "4","",""};
When i try to get common items form these two array using following code
var listCommon = list1.Intersect(list2);
It gives me result like this
string[] {"2", "3", "4", ""}
But i want it should return like this
string[] {"2", "3", "4", "", ""}
It is escaping last empty string value while intersecting.
Set methods like Intersect or Except remove duplicates from each collection. I assume you want something like this instead:
var listCommon = list1.Where(list2.Contains);
which is not as efficient. This could be an optimization:
var l2Lookup = new HashSet<string>(list2);
var listCommon = list1.Where(l2Lookup.Contains);
This will work:
list1.Where(x=>list2.Contains(x))

Logic to skip repeating values in a variable

i have a loop where a variable value will change in each loop and display those values in each loop. i need to skip the display of the value if the same value repeats from second time
You need to remove the duplicates from the list. Ive chosen StringCollection from the System.Collections.Specialized namespace. But you could use List from System.Collections.Generic
String[] strings = new String[] { "1", "2", "3", "4", "2", "5", "4", "6", "7" };
StringCollection unique = new StringCollection();
foreach (String s in strings)
{
if (!unique.Contains(s))
unique.Add(s);
}
foreach (String s in unique)
{
Console.WriteLine(s);
}
in speudo code
declare var1
for each item in the collection
check if item is var1, if not print item
set item to var1

Categories