If I have an excelsheet like
Name, age, ID;
Peter, 35, 123456;
Is there a way for me to locate that age is column numner 2, by searching for age in row 1, or similar?
What you can do is iterate through every column in the excel sheet and create a dictionary for every name/value pair. For example, 0 would map to Name, 1 would map to age and 2 would map to ID. From here, you may iterate through each row and for each column in that row look-up the name value pair (based on column ID). From there, you'll be able to determine the age.
Is there a way for me to locate that age is column numner 2, by searching for age in row 1, or similar?
Yes. Assuming the rows are really kept in the format you specified, separated by a comma, you can easily use string's Split method, and Linq's Select method:
string row = "Name, age, ID";
int columnNum = Array.IndexOf(row.Split(',')
.Select(x => x.Trim()).ToArray(), "age") + 1;
Explanation:
row.Split(',') - this method splits the string into an Array of strings: { "Name", "age", "ID" }
.Select(x => x.Trim()).ToArray() - this expression use LINQ to eliminate all the unnecessary spaces in the column Name (the method Trim() removes spaces at the beginning and at the end of the string).
Array.IndexOf - This method finds the index of the desired value ("age") within the array.
Indexes in C# begins at zero. namely, the index of "Name" is 0, and the index of "age" is actually 1 (and so on). To solve this I simply add 1 to the number returned by "IndexOf".
I'm warmly recommend to read any C# basic tutorial. it's all there :)
Check the example of string search in Excel from MSDN:
http://msdn.microsoft.com/en-us/library/e4x1k99a.aspx
Related
Eg: I have 2020M01 ,2019M12,2020M03 in datarow[].
How can i fetch max value i.e 2020M03
Your date format looks like it can be string sorted:
var dates = new System.Collections.Generic.List<string> { "2020M01", "2019M02", "2020M03" };
var max = dates.OrderByDescending(x => x).FirstOrDefault();
Or, as #panagiotis points out, Max() would also work:
var max = dates.Max();
This isn't an unusual format. Such formats ensure that date literals can be sorted alphabetically. YYYY-MM-DD and YYYYMMDD can be sorted alphabetically too.
This means that you can find the minimum or maximum value in a list simply by using the Min() or Max() LINQ functions, eg :
var months=new[]{ "2020M01" ,"2019M12","2020M03"};
var latestMonth=months.Max();
var earliestMonth=months.Min();
You say you have an array of DataRow, so I assume your dates must be in some column of the row
I'd thus say you need something like:
myDataRowArray.Max(ro => ro["nameOfYourDateColumn"].ToString());
If you mean that all your dates are in different columns of the same datarow, it's a bit more tricky. If there is nothing else in the row other than these dates, then it can be done with the row's ItemArray, an array of object representing each value of row's cells:
myDataRow.ItemArray.Max(elem => elem.ToString());
If there are some columns of the datarow that are your dates and some that are not, you're going to need to pull them out. Here I extract 3 different columns and put their values to a string array, then find the max:
new[] {
myRow["date1Column"].ToString(),
myRow["date2Column"].ToString(),
myRow["date3Column"].ToString()
}.Max();
I am attempting to import a .CSV file into my database which is a table export from an image management system. This system allows end-users to take images and (sometimes) split them into multiple images. There is a column in this report that signifies the file name of the image that I am tracking. If items are split in the image management system, the file name receives an underscore ("_") on the report. The previous file name is not kept. The way the items can possibly exist on the CSV are shown below:
Report 1 # 8:00AM: ABC.PNG
Report 2 # 8:30AM: ABC_1.PNG
ABC_2.PNG
Report 3 # 9:00AM: ABC_1_1.PNG
ABC_1_2.PNG
ABC_2_1.PNG
ABC_2_2.PNG
Report 4 # 9:30AM ABC_1_1_1.PNG
ABC_1_1_2.PNG
ABC_1_2.PNG
ABC_2_1.PNG
ABC_2_2.PNG
I am importing each file name into its own record. When an item is split, I would like to identify the previous version and update the original record, then add the new split record into my database. The key to knowing if an item is split is locating an underscore ("_").
I am not sure what I should do to recreate previous child names, I have to test every previous iteration of the file name to see if it exists. My problem is interpreting the current state of the file name and rebuilding all previous possibilities. I do not need the original name, only the first possible split name up until the current name. The code below shows kind of what I am getting at, but I am not sure how to do this cleanly.
String[] splitName = theStringToSplit.Split('_');
for (int i = 1; i < splitName.Length - 1; i++)
{
//should concat everything between 0 and i, not just 0 and I
//not sure if this is the best way or what I should do
MessageBox.Show(splitName[0] + "_" + splitName[i] + ".PNG");
}
The thing you are looking for is part of string.
So string.Join() might help you joining an array to a delimited string:
It also contains a parameter start index and number of items to use.
string[] s = new string[] { "2", "a", "b" };
string joined = string.Join("_", s, 0 ,3);
// joined will be "2_a_b"
Maybe you are using the wrong tool for you problem. If you want to keep the last "_", you may want to use LastIndexOf() or even Regular Expressions. Anyways: You should not unnecessarily rip of names and re-glue them. If done, do it cultrue invariant and not culture specific (there might be different interpretations of "-" or the low letter of "I".
string fnwithExt = "Abc_12_23.png";
string fn = System.IO.Path.GetFileName(fnwithExt);
int indexOf = fn.LastIndexOf('_');
string part1 = fn.Substring(0, indexOf-1);
string part2 = fn.Substring(indexOf+1);
string part3 = System.IO.Path.GetExtension(fnwithExt);
string original = System.IO.Path.ChangeExtension(part1 + "_"+ part2, part3);
I have a text file named my_date.txt containing following data:
1 Adam
2 Steve
3 Lisa
4 Josh
.....
The text file may be very long. I am trying to load this data contained in this text file into an array in C# so that I could do an operation. In sas I just use input. In VBA I just refer the cells, assuming I make it in excel. But here with C#, I have no idea at all.
#1 Simple For
You can use File.ReadAllLines to put the lines of a text file into a string array.
string[] names = File.ReadAllLines("C:\\my_date.txt");
And then parse the data to remove the 1, 2, 3, etc before the names
for (int i = 0; i < names.Length; i++)
{
names[i] = names[i].Split()[1];
}
#2 LINQ
Using the simple for loop will work fine, but alternatively you can use LINQ:
string[] names = File.ReadAllLines("C:\\my_date.txt")
.Select(str => str.Split()).Select(name => name[1]).ToArray();
In the event that you don't need a number prefix, you can simply use the ReadAllLines method without the Split()
In C# you can do that using File.ReadLines method and LINQ:
var values = File
.ReadLines("filePath") // 1
.Select(x => x.Split()) // 2
.Select(x => new { Id = x[0], Name = string.Join(" ", x.Skip(1) }) // 3
.ToArray(); // 4
Read all lines from the file
Split each line by white-space
Create an anonymous object for each line that contains two property Id (number), and the Name, I used string.Join because your names might contain white-spaces.You can use a custom class instead of anonymous type that would be more appropriate.
Convert the result into an array.
i'm learning programming in C# and would like to know if it is possible to output the value of a string that is 12 letters long into a table with 12 columns, each column will have one label which one letter of the string will be displayed in
Sure. Just iterate the characters and do whatever you want. And it would go a little something like this:
// create an instance of your table, whatever it may be.
// create an instance of a row
// add row to your table
var line = "hello world";
foreach (var letter in line)
{
// create an instance of a column
// add column to your row
// add label to your column
// set text property of lable = letter
}
Have a look at the String.Format method:
http://msdn.microsoft.com/en-us/library/system.string.format.aspx
Having a bit of trouble with converting a comma separated text file to a generic list. I have a class (called "Customers") defined with the following attributes:
Name (string)
City (string)
Balance (double)
CardNumber (int)
The values will be stored in a text file in this format: Name,City, Balance, CarNumber e.g. John,Memphis,10,200789. There will be multiple lines of this. What I want to do is have each line be placed in a list item when the user clicks a button.
I've worked out I can break each line up using the .Split() method, but have no idea how to make the correct value go into the correct attribute of the list. (Please note: I know how to use get/set properties, and I am not allowed to use LINQ to solve the problem).
Any help appreciated, as I am only learning and have been working on this for a for while with no luck. Thanks
EDIT:
Sorry, it appears I'm not making myself clear. I know how to use .add.
If I have two lines in the text file:
A,B,1,2 and
C,D,3,4
What I don't know how to do is make the name "field" in the list item in position 0 equal "A", and the name "field" in the item in position 1 equal "C" and so on.
Sorry for the poor use of terminology, I'm only learning. Hope you understand what I'm asking (I'm sure it's really easy to do once you know)
The result of string.Split will give you an array of strings:
string[] lineValues = line.Split(',');
You can access values in an array by index:
string name = lineValues[0];
string city = lineValues[1];
You can convert strings to double or int using their respective Parse methods:
double balance = double.Parse(lineValues[2]);
int cardNumber = int.Parse(lineValues[3]);
You can instantiate the class and assign to it very simply:
Customer customerForCurrentLine = new Customer()
{
Name = name,
City = city,
Balance = balance,
CardNumber = cardNumber,
};
Simply loop over the lines, instantiate a Customer for that line, and add it to a variable you've created of the type List<Customer>
If you want your program to be bulletproof, you're going to have to do a lot of checking to skip over lines that don't have enough values, or that would fail to parse to the correct number type. For example, check lineValues.Length == 4 and use int.TryParse(...) and double.TryParse(...).
Read a file and split its text based on newline character. Then for total line count run a loop that will split based on comma and create a new object and insert values in its properties and add that object to a list.
This way
List<Customers> lst = new List<Customers>();
string[] str = System.IO.File.ReadAllText(#"C:\CutomersFile.txt")
.Split(new string[] { Environment.NewLine },
StringSplitOptions.None);
for (int i = 0; i < str.Length; i++)
{
string[] s = str[i].Split(',');
Customers c = new Customers();
c.Name = s[0];
c.City = s[1];
c.Balance = Convert.ToDouble(s[2]);
c.CardNumber = Convert.ToInt32(s[3]);
lst.Add(c);
}
BTW class name should be Customer and not Customers
Split() generates an array of strings in the order they appeared in the source string. Thus, if your name field is the first column in the CSV file, it will always be the first index in the array.
someCustomer.Name = splitResult[0];
And so on. You'll also need to investigate String.TryParse for your class's numerically typed properties.