I'm trying to remove an element/item/entry from a split string.
Let's say I got the string [string_] as follows:
string string_ = "one;two;three;four;five;six";
Then I split this string to get each, let's say, item:
string[] item = (string_.Split(";"));
I have no informations other than from variables. Depending on the user choice, I can get an item value and index.
Let's say that for this example, the user chose "four" which is the index "3".
How can I make my string look like the index 3 have been deleted, as string_ would be equal to the following:
"one;two;three;five;six"
I've tried multiple things and it seems like the only solution is to go through a char method.
Is that true or did I miss something?
EDIT to suggested already_posted_answer :
Not quite the same question as my ITEM could be placed anywhere in my splitted string depending on the user selection.
First of all you need to write better variable names, string_ is a horrible name. Even something like "input" is way better.
string input = "one;two;three;four;five;six";
Next, you are on the right track by using Split(). This will return an array of string:
string[] splitInput = input.Split(";");
The resulting string array will look like this:
//string[0] = one
//string[1] = two
//string[2] = three
//string[3] = four
//string[4] = five
//string[5] = six
Removing with known index
If you want to remove a specific element from the array, you could make the result of Split() a List<T> by using ToList() instead and utilize the RemoveAt() method of the resulting List<T>:
List<string> splitList = input.Split(';').ToList();
splitList.RemoveAt(3);
//Re-create the string
string outputString = string.Join(";", splitList);
//output is: "one;two;three;five;six"
Remove all strings that match an input
If you need to remove items from the list without knowing their index but knowing the actual string, you can use LINQ's Where() to filter out the matching items:
//Get the input from the user somehow
string userInput = Console.ReadLine();
IEnumerable<string> filteredList = input.Split(';')
.Where(x => string.Compare(x, userInput, true) != 0);
//Re-create the string
string outputString = string.Join(";", filteredList);
I made a fiddle to demonstrate both methods here
You can convert an array of string to list by following:
var list = new List<string>(item);
Once the list is created, you can easily remove an element:
var index = list.IndexOf("four");
list.RemoveAt(index);
Join the string back:
var result = String.Join(";", list.ToArray());
Result:
You can convert your string array into a List<string>, and since you have the index of the item to be removed, you can remove the item using RemoveAt, then join the items back into one string.
Here's a complete console application example:
static void Main(string[] args)
{
string string_ = "one;two;three;four;five;six";
string[] items = (string_.Split(';'));
Console.WriteLine("Please select an item to remove:");
for (int i = 0;i<items.Length;i++)
{
Console.WriteLine(string.Format("{0}- {1}", (i + 1).ToString(), items[i]));
}
int num = 0;
int.TryParse(Console.ReadLine(), out num);
if (num > 0 && num <= items.Length)
{
List<string> itemsList = items.ToList();
itemsList.RemoveAt(num - 1);
string newString = string.Join(";", itemsList);
Console.WriteLine(string.Format("The new string is: {0}", newString));
}
else
{
Console.WriteLine("Invalid number!");
}
Console.ReadLine();
}
Hope that helps.
We can employ LINQ.
Initial plan is to split the string, then create a union of two enumerables: before and after the item. Something like this:
// preconditions
const int idx = 3;
string string_ = "one;two;three;four;five;six";
// actual transformation
string[] item = (string_.Split(';'));
var iterator = item.Take(idx).Concat(item.Skip(idx + 1));
// output the results
var result = string.Join(";", iterator);
Console.Write(result);
Would this work for you?
If you create a new string like this, then replace the value of string_ with the value of the new string.
string string_ = "one;two;three;four;five;six";
string newstring = string_.Replace("four", "");
string_ = newstring.Replace(";;", ";");
So I've been trying to figure out how to delete characters after a certain point on each line, for example I have a list like:
dskfokes=dasfn3rewk
dsanfiwen=434efsde
damkw4343=o3rm3i
dmfkim303rk2=0439wefksd
32i32j9esfj=42393jdsf
How would I go about deleting everything on each line after '='?
Use string.IndexOf() to get the index of the char you want to remove, then string.Remove() to do the removing.
string str = "dskfokes=dasfn3rewk";
str = str.Remove(str.IndexOf('='));
One approach is to use LINQ:
var strings = new string[] {
"dskfokes=dasfn3rewk
, "dsanfiwen=434efsde
, "damkw4343=o3rm3i
, "dmfkim303rk2=0439wefksd
, "32i32j9esfj=42393jdsf
};
var res = strings.Select(s => s.Split('=')[0]).ToArray();
This splits each string on =, and drops everything after the first '=' character if it is there.
You may also do it using String.Split() like
string[] allWords = new string[] {
"dskfokes=dasfn3rewk",
"dsanfiwen=434efsde",
"damkw4343=o3rm3i",
"dmfkim303rk2=0439wefksd",
"32i32j9esfj=42393jdsf"
};
foreach(string s in allWords)
{
string[] urstring = s.Split('=');
Console.WriteLine(urstring[0]);
}
I suggest you to use a combination of string handling operations SubString and IndexOf to achieve this, consider the example:
List<string> inputLine = new List<string>(){ "dskfokes=dasfn3rewk",
"dsanfiwen=434efsde",
"damkw4343=o3rm3i",
"dmfkim303rk2=0439wefksd",
"32i32j9esfj=42393jdsf"};
List<string> outputLines = inputLine.Select(x =>
x.IndexOf('=') == -1 ? x :
x.Substring(0, x.IndexOf('='))).ToList();
Note : The IndexOf will return -1 if the specified index was not found, in such cases substring method will throws errors since -1 will not be a valid index. So we have to check for existence of index withing the string before proceeding. you can also try simple foreach as like this:
List<string> outputLines=new List<string>();
int currentCharIndex=-1;
foreach (string line in inputLine)
{
currentCharIndex = line.IndexOf('=');
if(currentCharIndex ==-1)
outputLines.Add(line);
else
outputLines.Add(line.Substring(0,currentCharIndex));
}
I have a text-file with many lines, each line looks like this:
"string string double double" between each value is a space. I'd like to read out the first string and last double of every line and put these two values in a existing list. That is my code so far, but it doesnt really work.
private void bOpen_Click(object sender, RoutedEventArgs e)
{
bool exists = File.Exists(#"C:\Users\p2\Desktop\Liste.txt");
if (exists == true)
{
StringBuilder sb = new StringBuilder();
using (StreamReader sr = new StreamReader(#"C:\Users\p2\Desktop\Liste.txt"))
{
Vgl comp = new Vgl();
comp.name = Abzahlungsdarlehenrechner.zgName;
comp.gErg = Abzahlungsdarlehenrechner.zgErg;
GlobaleDaten.VglDaten.Add(comp);
int i = 0;
string line = File.ReadLines(#"Liste.txt").Skip(0).Take(1).First();
while ((line = sr.ReadLine()) != null)
{
sb.Append((line));
listBox.Items.Add(line);
GlobaleDaten.VglDaten.Add(comp);
i++;
}
}
}
I have already read this, but it didnt help How do I read specific value[...]
You can try Linq:
var source = File
.ReadLines(#"C:\Users\p2\Desktop\Liste.txt")
.Select(line => line.Split(' '))
.Select(items => new Vgl() {
name = items[0],
gErg = double.Parse(items[3])
});
// If you want to add into existing list
GlobaleDaten.VglDaten.AddRange(source);
// If you want to create a new list
//List<Vgl> list = source.ToList();
how about
List<Vgl> Result = File.ReadLines(#"C:\Users\p2\Desktop\Liste.txt")
.Select(x => new Vgl()
{
name = x.Split(' ').First(),
gErg = decimal.Parse(x.Split(' ').Last(), NumberStyles.AllowCurrencySymbol)
})
.ToList();
I would avoid storing money within doulbe values because this could lead to rounding issues. Use decimal instead. Examples here: Is a double really unsuitable for money?
You can use:
string[] splitBySpace = line.Split(' ');
string first = splitBySpace.ElementAt(0);
decimal last = Convert.ToDecimal(splitBySpace.ElementAt(splitBySpace.Length - 1));
Edit : To Handle Currency symbol:
string[] splitBySpace = line.Split(' ');
string pattern = #"[^0-9\.\,]+";
string first = splitBySpace.ElementAt(0);
string last = (new Regex(pattern)).Split(splitBySpace.ElementAt(splitBySpace.Length - 1))
.FirstOrDefault();
decimal lastDecimal;
bool success = decimal.TryParse(last, out lastDecimal);
I agree with #Dmitry and fubo, if you are looking for alternatives, you could try this.
var source = File
.ReadLines(#"C:\Users\p2\Desktop\Liste.txt")
.Select(line =>
{
var splits = line.Split(' '));
return new Vgl()
{
name = splits[0],
gErg = double.Parse(splits[3])
};
}
use string.split using space as the delimiter on line to the string into an array with each value. Then just access the first and last array element. Of course, if you aren't absolutely certain that each line contains exactly 4 values, you may want to inspect the length of the array to ensure there are at least 4 values.
reference on using split:
https://msdn.microsoft.com/en-us/library/ms228388.aspx
Read the whole file as a string.
Split the string in a foreach loop using \r\n as a row separator. Add each row to a list of strings.
Iterate through that list and split again each record in another loop using space as field separator and put them into another list of strings.
Now you have all the four fields containig one row. Now just use First and Last methods to get the first word and the last number.
I want to remove comma separated duplicate string values like :
String str = "2,4,3,12,25,2,4,3,6,2,2,2";
And i want to output like this:
String str1 = "6,2";
please tell how to do this i'll my self but i can't solve this
A wild ride with Linq. Probably there is a better way, but this is the first one I could think of.
string str = "2,4,3,12,25,2,4,3,6,2,2,2";
List<string> uniques = str.Split(',').Reverse().Distinct().Take(2).Reverse().ToList();
string newStr = string.Join(",", uniques);
Console.WriteLine(newStr);
Split the string at the comma to get the sequence
Apply the Reverse op, you get 2 2 2 6 .... 4 2
Apply the Distinct, you get 2,6,3,4,25,12
Take the first 2 elements (2,6)
Reverse them 6,2
Join in a new string with the comma sep.
Pretty basic but works in your case
String str = "2,4,3,12,25,2,4,3,6,2,2,2";
String[] arr = str.Split(',');
String penultimate = "";
String ultimate = "";
for (int i = 0; i < arr.Length; i++)
{
if (arr[i] != ultimate)
{
penultimate = ultimate;
ultimate = arr[i];
}
}
Console.WriteLine("{0},{1}", penultimate, ultimate);
Here is a suggestion:
string item = "";
var lastTwoUnique= str.Split(',') //split the string on ,
//now, take the next element from the array as long as it's
//not equal to the previous element (which we store in item)
.Where((st) => st==item ? false : (item = st) == item) //** see comment below
.Reverse() //reverse collection
.Take(2) //take two (two last)
.Reverse() //reverse back
.ToList(); //make it a list
var answer = string.Join(",", lastTwoUnique);
This solution keeps the data intact, so if you want you could store the unique list, then do many queries on that list. Solutions using Distinct() will, for instance, not keep every occurrence of 2 in the list.
This solution has the intermediate result (after Where) of: 2,4,3,12,25,2,4,3,6,2. While distinct will be:2,4,3,12,25,6
** The line .Where((st) => st==item ? false : (item = st) == item) may seem odd, so let me explain:
Where takes a lambda function that returns true for items that should be taken, and false for the items that should be ignored. So st will become each sub string from the Split.
Now, let's investigate the actual function:
st==item //is this st equal to the previous item?
? false //then return false
: (item = st) == item //if it's not equal, then assign `item` to the current `st`
//and compare that to item and get `true`
You could use the .Distinct() extension method.
String str = "2,4,3,12,25,2,4,3,6,2,2,2";
var oldArray=str.Split(',').Reverse();
var collectionWithDistinctElements = oldArray.Distinct().ToArray();
var reverse=collectionWithDistinctElements.Reverse();
//take two element
var twoElements=reverse.ToList().Take(2);
//last join them
var resultArray=string.Join(",", twoElements);
Another solution, which I've attempted to keep quite simple:
String str = "2,4,3,12,25,2,4,3,6,2,2,2";
var holder = new string[2];
foreach (var x in str.Split(','))
{
if(holder.Last() != x)
{
holder[0] = holder[1];
holder[1] = x;
}
}
var result = string.Join(",", holder);
This will iterate over the comma-separated items, all the time keeping the two last seen distinct items in holder.
String str = "2,4,3,12,25,2,4,3,6,2,2,2";
string str = s1;
var uniques = str.Split(',').Reverse().Distinct().Take(3).Reverse().Take(2).ToList();
string newStr = string.Join(",", uniques.ToArray());
This will give me correct output that is 3,6 thats i want.
Thanks to all the Guys that give me ans.
This will definitely work
string str = "2,4,3,12,25,2,4,3,6,2,2,2";
List<string> uniques = new List<string>()
uniques = str.Split(',').Reverse().Distinct().Take(2).Reverse().ToList();
string newStr = string.Join(",", uniques);
I have an array/list/collection/etc of objects. For sample purposes, lets assume it is just a string array/list/collection/etc.
I want to iterate through the array and split certain elements based on certain criteria. This is all handled by my object. So once I have the object index that I want to split, what is the standard way of splitting the object and then reinserting it back into the original array in order. I'll try and demonstrate what I mean using a string array:
string[] str = { "this is an element", "this is another|element", "and the last element"};
List<string> new = new List<string>();
for (int i = 0; i < str.Length; i++)
{
if (str[i].Contains("|")
{
new.AddRange(str[i].Split("|"));
}
else
{
new.Add(str[i]);
}
}
//new = { "this is an element", "this is another", "element", "and the last element"};
This code works and everything, but is there a better way to do this? Is there a known design pattern for this; for like an inplace array split?
For this particular example, you could utilize SelectMany to get your new array.
string[] array = { "this is an element", "this is another|element", "and the last element" };
string[] newArray = array.SelectMany(s => s.Split('|')).ToArray();
// or List<string> newList = array.SelectMany(s => s.Split('|')).ToList();
// or IEnumerable<string> projection = array.SelectMany(s => s.Split('|'));
You can do this:
List<string> newStr = str.SelectMany(s => s.Split('|')).ToList();