C# I have two lists. I want to compare them - c#

I have a very complex problem. At least to me it is, since I am a beginner.
I have 2 List(string) lists.
One of them is filled with currency ISO codes. Second is their value. Both lists have 332 lines.
I want to compare a Console.ReadLine(); input with the currency ISO codes list.
If it is contained in the list to get it's row number.
Then get that row number and use it to get the same row from the value list.
Here is the code:
download = empty16.Replace(download, "");
StringBuilder sb1 = new StringBuilder();
for (int iaU = 0; iaU < download.Length; iaU++)
{
if (iaU%3 == 0)
sb1.Append('\n');
sb1.Append(download[iaU]);
}
string formDown = sb1.ToString();
List<string> formFin = formDown.Split('\n').ToList(); //This is the ISO list
List<string> l1st = new List<string>();
int iwNz = 0;
while (iwNz < intVal)
{
string sub = formIvx.Substring(iwNz);
//Console.WriteLine(sub);
l1st.Add(sub);
iwNz += intVal;
}

You want something like this:
string input = Console.ReadLine();
int index = formFin.IndexOf(input);
if(index != -1)
{
var value = valueList[index];
}

Related

How can I split a string to store contents in two different arrays in c#?

The string I want to split is an array of strings.
the array contains strings like:
G1,Active
G2,Inactive
G3,Inactive
.
.
G24,Active
Now I want to store the G's in an array, and Active or Inactive in a different array. So far I have tried this which has successfully store all the G's part but I have lost the other part. I used Split fucntion but did not work so I have tried this.
int i = 0;
for(i = 0; i <= grids.Length; i++)
{
string temp = grids[i];
temp = temp.Replace(",", " ");
if (temp.Contains(' '))
{
int index = temp.IndexOf(' ');
grids[i] = temp.Substring(0, index);
}
//System.Console.WriteLine(temp);
}
Please help me how to achieve this goal. I am new to C#.
If I understand the problem correctly - we have an array of strings Eg:
arrayOfStrings[24] =
{
"G1,Active",
"G2,Inactive",
"G3,Active",
...
"G24,Active"
}
Now we want to split each item and store the g part in one array and the status into another.
Working with arrays the solution is to - traverse the arrayOfStrings.
Per each item in the arrayOfStrings we split it by ',' separator.
The Split operation will return another array of two elements the g part and the status - which will be stored respectively into distinct arrays (gArray and statusArray) for later retrieval. Those arrays will have a 1-to-1 relation.
Here is my implementation:
static string[] LoadArray()
{
return new string[]
{
"G1,Active",
"G2,Inactive",
"G3,Active",
"G4,Active",
"G5,Active",
"G6,Inactive",
"G7,Active",
"G8,Active",
"G9,Active",
"G10,Active",
"G11,Inactive",
"G12,Active",
"G13,Active",
"G14,Inactive",
"G15,Active",
"G16,Inactive",
"G17,Active",
"G18,Active",
"G19,Inactive",
"G20,Active",
"G21,Inactive",
"G22,Active",
"G23,Inactive",
"G24,Active"
};
}
static void Main(string[] args)
{
string[] myarrayOfStrings = LoadArray();
string[] gArray = new string[24];
string[] statusArray = new string[24];
int index = 0;
foreach (var item in myarrayOfStrings)
{
var arraySplit = item.Split(',');
gArray[index] = arraySplit[0];
statusArray[index] = arraySplit[1];
index++;
}
for (int i = 0; i < gArray.Length; i++)
{
Console.WriteLine("{0} has status : {1}", gArray[i] , statusArray[i]);
}
Console.ReadLine();
}
seems like you have a list of Gxx,Active my recomendation is first of all you split the string based on the space, which will give you the array previoulsy mentioned doing the next:
string text = "G1,Active G2,Inactive G3,Inactive G24,Active";
string[] splitedGItems = text.Split(" ");
So, now you have an array, and I strongly recommend you to use an object/Tuple/Dictionary depends of what suits you more in the entire scenario. for now i will use Dictionary as it seems to be key-value
Dictionary<string, string> GxListActiveInactive = new Dictionary<string, string>();
foreach(var singleGItems in splitedGItems)
{
string[] definition = singleGItems.Split(",");
GxListActiveInactive.Add(definition[0], definition[1]);
}
What im achiving in this code is create a collection which is key-value, now you have to search the G24 manually doing the next
string G24Value = GxListActiveInactive.FirstOrDefault(a => a.Key == "G24").Value;
just do it :
var splitedArray = YourStringArray.ToDictionary(x=>x.Split(',')[0],x=>x.Split(',')[1]);
var gArray = splitedArray.Keys;
var activeInactiveArray = splitedArray.Values;
I hope it will be useful
You can divide the string using Split; the first part should be the G's, while the second part will be "Active" or "Inactive".
int i;
string[] temp, activity = new string[grids.Length];
for(i = 0; i <= grids.Length; i++)
{
temp = grids[i].Split(',');
grids[i] = temp[0];
activity[i] = temp[1];
}

C# Populate An Array with Values in a Loop

I have a C# console application where an external text file is read. Each line of the file has values separated by spaces, such as:
1 -88 30.1
2 -89 30.1
So line one should be split into '1', '-88', and '30.1'.
What I need to do is to populate an array (or any other better object) so that it duplicate each line; the array should have 3 elements per row. I must be having a brain-lock to not figure it out today. Here's my code:
string line;
int[] intArray;
intArray = new int[3];
int i = 0;
//Read Input file
using (StreamReader file = new StreamReader("Score_4.dat"))
{
while ((line = file.ReadLine()) != null && line.Length > 10)
{
line.Trim();
string[] parts;
parts = line.Split(' ');
intArray[0][i] = parts[0];//error: cannot apply indexing
i++;
}
}
Down the road in my code, I intend to make some API calls to a server by constructing a Json object while looping through the array (or alternate object).
Any idea?
Thanks
If you only need the data to be transferred to JSON then you don't need to process the values of the data, just reformat it to JSON arrays.
As you don't know the number of lines in the input file, it is easier to use a List<>, whose capacity expands automatically, to hold the data rather than an array, whose size you would need to know in advance.
I took your sample data and repeated it a few times into a text file and used this program:
static void Main(string[] args)
{
string src = #"C:\temp\Score_4.dat";
List<string> dataFromFile = new List<string>();
using (var sr = new StreamReader(src))
{
while (!sr.EndOfStream)
{
string thisLine = sr.ReadLine();
string[] parts = thisLine.Split(" ".ToCharArray(), StringSplitOptions.RemoveEmptyEntries);
if (parts.Length == 3)
{
string jsonArray = "[" + string.Join(",", parts) + "]";
dataFromFile.Add(jsonArray);
}
else
{
/* the line did not have three entries */
/* Maybe keep a count of the lines processed to give an error message to the user */
}
}
}
/* Do something with the data... */
int totalEntries = dataFromFile.Count();
int maxBatchSize = 50;
int nBatches = (int)Math.Ceiling((double)totalEntries / maxBatchSize);
for(int i=0;i<nBatches;i+=1)
{
string thisBatchJsonArray = "{\"myData\":[" + string.Join(",", dataFromFile.Skip(i * maxBatchSize).Take(maxBatchSize)) + "]}";
Console.WriteLine(thisBatchJsonArray);
}
Console.ReadLine();
}
to get this output:
{"myData":[[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1]]}
{"myData":[[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1],[1,-88,30.1],[2,-89,30.1]]}
It should be easy to adjust the format as required.
I would create a custom Item class and then populate a list, for easy access and sorting, with self contained items. something like:
public Class MyItem
{
public int first { get; set; }
public int second { get; set; }
public float third { get; set; }
public MyItem(int one, int two, float three)
{
this.first = one;
this.second = two;
this.third = three;
}
}
then you could do:
List<MyItem> mylist = new List<MyItem>();
and then in your loop:
using (StreamReader file = new StreamReader("Score_4.dat"))
{
while ((line = file.ReadLine()) != null && line.Length > 10)
{
line.Trim();
string[] parts;
parts = line.Split(' ');
MyItem item = new Item(Int32.Parse(parts[0]),Int32.Parse(parts[1]),Float.Parse(parts[2]));
mylist.Add(item);
i++;
}
}
As there are numbers like 30.1 so int is not suitable for this, and also it must not be a double[] but double[][]:
string[] lines = File.ReadAllLines("file.txt");
double[][] array = lines.Select(x => s.Split(' ').Select(a => double.Parse(a)).ToArray()).ToArray();
Issue is that int array is single dimensional.
My suggestion is that you can put a class with 3 properties and populate a list of class there. It's better to have class with same property names that you require to build JSON. So that you can easily serialize this class to JSON using some nugets like Newtonsoft and make api calls easily.
Your int array is a single dimensional array yet you're trying to index it like a multidemensional array. It should be something like this:
intArray[i] = parts[0]
(However you'll need to handle converting to int for parts that are fractional)
Alternatively, if you want to use a multidimensional array, you have to declare one.
int[][] intArray = new int[*whatever your expected number of records are*][3]
Arrays have a static size. Since you're reading from a file and may not know how many records there are until your file finishes reading, I recommend using something like a List of Tuples or a Dictionary depending on your needs.
A dictionary will allow you to have quick lookup of your records without iterating over them by using a key value pair, so if you wanted your records to match up with their line numbers, you could do something like this:
Dictionary<int, int[]> test = new Dictionary<int, int[]>();
int lineCount = 1;
while ((line = file.ReadLine()) != null && line.Length > 10)
{
int[] intArray = new int[3];
line.Trim();
string[] parts = line.Split(' ');
for (int i = 0; i < 3; i++)
{
intArray[i] = int.Parse(parts[i]);
}
test[lineCount] = intArray;
lineCount++;
}
This will let you access your values by line count like so:
test[3] = *third line of file*

All permutations of form options

I'm trying to test a form by submitting a combination of all values to see if it breaks. These are ComboBoxes that I have stored in an ExtraField class
public class ExtraField
{
public String Name = ""; //name of form key
public Dictionary<String, String> Options = new Dictionary<String, String>(); //Format: OptionText, Value
}
I have generated a list of these fields
List<ExtraField> efList = new List<ExtraField>();
I was thinking all possible combinations of these fields could be added to a string list that I can parse (I was thinking name=opt|name=opt|name=opt). I've provided an example of what would work below (where ExtraField list Count==3):
List<ExtraField> efList = new List<ExtraField>();
ExtraField f1 = new ExtraField();
f1.Name = "name1";
f1.Options.Add("text", "option1");
f1.Options.Add("text2", "option2");
f1.Options.Add("text3", "option3");
efList.Add(f1);
ExtraField f2 = new ExtraField();
f2.Name = "name2";
f2.Options.Add("text", "option1");
f2.Options.Add("text2", "option2");
f2.Options.Add("text3", "option3");
f2.Options.Add("text4", "option4");
efList.Add(f2);
ExtraField f3 = new ExtraField();
f3.Name = "name3";
f3.Options.Add("text2", "option1");
f3.Options.Add("text3", "option2");
f3.Options.Add("text4", "option3");
f3.Options.Add("text5", "option4");
f3.Options.Add("text6", "option5");
efList.Add(f3);
Should produce
name1=option1|name2=option1|name3=option1
name1=option1|name2=option1|name3=option2
name1=option1|name2=option1|name3=option3
name1=option1|name2=option1|name3=option4
name1=option1|name2=option1|name3=option5
name1=option1|name2=option2|name3=option1
name1=option1|name2=option2|name3=option2
name1=option1|name2=option2|name3=option3
name1=option1|name2=option2|name3=option4
name1=option1|name2=option2|name3=option5
name1=option1|name2=option3|name3=option1
name1=option1|name2=option3|name3=option2
name1=option1|name2=option3|name3=option3
name1=option1|name2=option3|name3=option4
name1=option1|name2=option3|name3=option5
name1=option1|name2=option4|name3=option1
name1=option1|name2=option4|name3=option2
name1=option1|name2=option4|name3=option3
name1=option1|name2=option4|name3=option4
name1=option1|name2=option4|name3=option5
name1=option2|name2=option1|name3=option1
...etc
All ExtraFields in the list need to have a value and I need all permutations in one format or another. It's a big list with a lot of permutations otherwise I'd do it by hand.
Well I did it... But I'm not proud of it. I'm sure there is a better way of doing it recursively. Hopefully this helps someone.
public List<String> GetFormPermutations(List<ExtraField> inList)
{
List<String> retList = new List<String>();
int[] listIndexes = new int[inList.Count];
for (int i = 0; i < listIndexes.Length; i++)
listIndexes[i] = 0;
while (listIndexes[inList.Count-1] < inList.ElementAt(inList.Count-1).Options.Count)
{
String cString = "";
//after this loop is complete. a line is done.
for (int i = 0; i < inList.Count; i++) {
String key = inList.ElementAt(i).Name;
Dictionary<String, String> cOptions = inList.ElementAt(i).Options;
String value = cOptions.ElementAt(listIndexes[i]).Value;
cString += key + "=" + value;
if (i < inList.Count - 1)
cString += "|";
}
retList.Add(cString);
listIndexes[0]++;
for(int i = 0; i < inList.Count -1; i++)
{
if (listIndexes[i] >= inList.ElementAt(i).Options.Count)
{
listIndexes[i] = 0;
listIndexes[i + 1]++;
}
}
}
return retList;
}
UPDATED ANSWER
So I managed to do it recursively. I haven't done this since college :D
Here's the whole class:
https://gist.github.com/Rastamas/8070ae7e1471d2183451a17bcf061376
PREVIOUS ANSWER BELOW
This goes through your list and adds the strings to a StringBuilder in the format you showed
foreach (var item in efList)
{
foreach (var option in item.Options)
{
stringBuilder.Append(String.Format("{0}={1}|", item.Name, option.Value));
}
stringBuilder.Remove(stringBuilder.Length - 1, 1);
stringBuilder.AppendLine();
}
Then you can just use stringBuilder.ToString() to get the whole list.

How to get an index of a word in string array

I want to get the index of a word in a string array.
for example, the sentence I will input is 'I love you.'
I have words[1] = love, how can I get the position of 'love' is 1? I could do it but just inside the if state. I want to bring it outside. Please help me.
This is my code.
static void Main(string[] args)
{
Console.WriteLine("sentence: ");
string a = Console.ReadLine();
String[] words = a.Split(' ');
List<string> verbs = new List<string>();
verbs.Add("love");
int i = 0;
while (i < words.Length) {
foreach (string verb in verbs) {
if (words[i] == verb) {
int index = i;
Console.WriteLine(i);
}
} i++;
}
Console.ReadKey();
}
I could do it but just inside the if state. I want to bring it outside.
Your code identifies the index correctly, all you need to do now is storing it for use outside the loop.
Make a list of ints, and call Add on it for the matches that you identify:
var indexes = new List<int>();
while (i < words.Length) {
foreach (string verb in verbs) {
if (words[i] == verb) {
int index = i;
indexes.Add(i);
break;
}
}
i++;
}
You can replace the inner loop with a call of Contains method, and the outer loop with a for:
for (var i = 0 ; i != words.Length ; i++) {
if (verbs.Contains(words[i])) {
indexes.Add(i);
}
}
Finally, the whole sequence can be converted to a single LINQ query:
var indexes = words
.Select((w,i) => new {w,i})
.Where(p => verbs.Contains(p.w))
.Select(p => p.i)
.ToList();
Here is an example
var a = "I love you.";
var words = a.Split(' ');
var index = Array.IndexOf(words,"love");
Console.WriteLine(index);
private int GetWordIndex(string WordOrigin, string GetWord)
{
string[] words = WordOrigin.Split(' ');
int Index = Array.IndexOf(words, GetWord);
return Index;
}
assuming that you called the function as GetWordIndex("Hello C# World", "C#");, WordOrigin is Hello C# World and GetWord is C#
now according to the function:
string[] words = WordsOrigin.Split(' '); broke the string literal into an array of strings where the words would be split for every spaces in between them. so Hello C# World would then be broken down into Hello, C#, and World.
int Index = Array.IndexOf(words, GetWord); gets the Index of whatever GetWord is, according to the sample i provided, we are looking for the word C# from Hello C# World that is then splitted into an Array of String
return Index; simply returns whatever index it was located from

How to populate a RadioButton List with 4 answer choices in random order for a Quiz?

I am trying to create a quiz widget based off of SharePoint list data (Questions and 4 answer choices).
I am able to find a way to pull 10 random rows and read the questions and answers.
However, what I cant seem to come up with is logic to populate the RadioButton list with the answer choices (for that specific row item) in a random order.
Here is the code I have thus far: Please suggest possible strategies/code
//Function to pull 10 random questions from the "QuestionsAndAnswers" list for the correspoding LessonPlan
public void LoadQuestions()
{
try
{
SPWeb thisWeb = SPContext.Current.Web;
//Accessing the list correspoding to the current LessonPLan subsute
SPList oSPList = thisWeb.Lists["QuestionsAndAnswers"];
//Using a query in case there is a need tofilter by LessonID
SPQuery oSPQuery = new SPQuery();
oSPQuery.RowLimit = 10;
SPListItemCollection oSPListItemCollection = oSPList.GetItems(oSPQuery);
Random rand = new Random();
List <int> tempStore = new List<int>();
List <int> tempStore2 = new List<int>();
int tempValue = 0;
//int tempValue2 = 0;
int icount = 0;
int iMax = oSPListItemCollection.Count;
//int icount2 = 0;
//int iMax2 = oSPListItemCollection.Count;
SPListItem thisItem;
Label thisQuestion;
Label thisCorrectAnswer;
RadioButtonList thisAnswers;
while (icount < 10)
{
tempValue = rand.Next(1, iMax);
if (tempStore.Exists(value => value == tempValue))
continue;
else
{
tempStore.Add(tempValue);
thisQuestion = (Label) UpdatePanelMaster.FindControl("Question" + icount.ToString());
thisItem = oSPListItemCollection[tempValue];
thisQuestion.Text= thisItem["Question"].ToString();
//Inside loop to handle random answer arrangements
thisAnswers = (RadioButtonList) UpdatePanelMaster.FindControl("RadioButtonList" + icount.ToString());
//The following 4 lines of code populates the RadioButton List only in order on every row item run
//How to randomize the order?
thisAnswers.Items.Add(thisItem["CorrectAnswer"].ToString();
thisAnswers.Items.Add(thisItem["IncorrectAnswer1"].ToString();
thisAnswers.Items.Add(thisItem["IncorrectAnswer2"].ToString();
thisAnswers.Items.Add(thisItem["IncorrectAnswer3"].ToString();
thisCorrectAnswer = (Label) UpdatePanelMaster.FindControl("CorrectAnswer" + icount.ToString());
thisCorrectAnswer.Text= thisItem["CorrectAnswer"].ToString();
}
tempValue = 0;
icount++;
}
}
//End random question handling
catch (Exception ex)
{
throw ex;
}
}
Try using LINQ:
// start with an array of the question key strings
new[] { "CorrectAnswer", "IncorrectAnswer1", "IncorrectAnswer2", "IncorrectAnswer3" }
// for each key string s, select the relevant answer string
.Select(s => thisItem[s].ToString())
// sort by a random number (i. e. shuffle)
.OrderBy(s => rand.Next())
// convert to a List<T> (for the ForEach method)
.ToList()
// for each answer string s in the list, add s to thisAnswers.Items
.ForEach(s => thisAnswers.Items.Add(s));

Categories