I am reading a column number from csv where the number is 123456791234567 however due to format it gets converted to
number="1.23457E+14" in the csv file.
is there any way where we can change it to original string using c# ?
I am trying with below code :
decimal number = Decimal.Parse(number,System.Globalization.NumberStyles.Any);
but the number i am getting is 123457000000000M and the actual number is 123456791234567
any idea on this?
If I understand correctly, excel is converting 123456791234567 to 1.23457E+14. In that case, you just need to format the excel cell (or potentially the column) containing the value to string, before you set the value.
If the C# program opens the csv to find the value to be 1.23457E+14, then there is no way for you to convert it back to 123456791234567, since the precision is already lost - unless of course the same value exists (or can be recreated) in other cells (columns)
Related
I'm facing a problem when reading the excel-sheet data using ExcelDataReader in c#.
I am reading data from excel-sheet(.xlsm)
One of the cell has a list of values to choose.
Eg.
5.1
5.2
5.1a
When I choose the value either 5.2 or 5.1a and read, I get the same exact value in the dataset
But when I choose 5.1 and read, I get 5.0999999999999996 in the dataset
Here is the code which I used to read the data in c#,
IExcelDataReader excelReader = ExcelReaderFactory.CreateOpenXmlReader(fileStream);
DataSet findingsData = excelReader.AsDataSet();
Note :
For a workaround, I put a space after the value 5.1 in the cell. Then it read the value exactly same as expected(5.1 instead of 5.0999999999999996).
But I'm wondering, when it read the value 5.2 exactly same without applying any space, why doesn't work for 5.1?
Any suggestions are welcome to resolve this issue...
Thanks,
Karthik
Take a look at this question: Why can't decimal numbers be represented exactly in binary?
My maths isn't quite up to figuring it out precisely (comments welcome) but I suspect that 5.1 doesn't convert to the C# double precisely, but 5.2 does.
The reason it works when you add the space is that Excel will assume that the field is text, the same way 5.1a is, but when it receives something that looks like a number it assumes it is a number. (You can see this behaviour in a default blank spreadsheet as it will be right aligned if it is a number and left aligned when you add a space or any other text).
I expect that if you explicitly format all the cells as text in your source spreadsheet then the value will be read as you expect
I have a list of ID in a matrix 'UserID'. I want create a xls or csv file that this UserID is its header lines. number of rows is:2200000 and number of columns is 11. Label of columns is years of 1996 - 2006 . I read this page :
https://www.mathworks.com/matlabcentral/answers/101309-how-do-i-use-xlswrite-to-add-row-and-column-labels-to-my-matlab-matrix-when-i-write-it-to-excel-in-m
but this code give me error. Although sometimes less is true for the number of rows and sometimes does not answer.Can anyone introduce a program that will do this? (with matlab or even c# code)
I write this code:
data=zeros(2200000,11);
data_cells=num2cell(data);
col_header={'1996','1997','1998','1999','2000','2001','2002','2003','2004','2005','2006'};
row_header(1:2200000,1)=UserID;
output_matrix=[{' '} col_header; row_header data_cells];
xlswrite('My_file.xls',output_matrix);
and I get this error:
The specified data range is invalid or too large to write to the specified file format. Try writing to an XLSX file and use Excel A1 notation for the range argument, for example, ‘A1:D4’.
When you use xlswrite you are limited to the number of rows that your Excel version permits:
The maximum size of array A depends on the associated Excel version.
In Excel 2013 the maximum is 1048576, which is 1151424 fewer rows than your 2200000x11 matrix.
You better use csvwrite to export your data, and refer also to the tip therein:
csvwrite does not accept cell arrays for the input matrix M. To export a cell array that contains only numeric data, use cell2mat to convert the cell array to a numeric matrix before calling csvwrite. To export cell arrays with mixed alphabetic and numeric data... you must use low-level export functions to write your data.
EDIT:
In your case, you should at least change this parts of the code:
col_header = 1996:2006;
output_matrix=[0, col_header; row_header data];
and you don't need to define output_matrix as a cell array (and don't need data_dells). However, you may also have to convert UserID to a numeric variable.
I have a grid control and I wanna get the value of the selected row. I could get the value of varchar type cell in row but I'm having trouble in getting the value for cell in decimal type.
Here's my code for every row click:
private void gridView1_RowClick(object sender, DevExpress.XtraGrid.Views.Grid.RowClickEventArgs e)
{
var productPrice = Convert.ToDecimal(gridView1.GetRowCellValue(gridView1.FocusedRowHandle, "product_price").ToString());
MessageBox.Show(productPrice.ToString());
}
For more info the product_price column is set to be in decimal type with length of (10,2) so the value its displaying is like 13,233.00
Thank you I hope you can help me to solve this problem
My first thought: Is there no focused row? Add this and see if it fixes the issue:
if (gridView1.SelectedRowsCount == 0)
return;
That wasn't the issue? Okay, add this to your code and set a breakpoint:
object o = gridView1.GetRowCellValue(gridView1.FocusedRowHandle, "product_price");
Type t = o.GetType();
When you add a watch (or hover) over t, does it say System.Decimal or String?
If it's a decimal, you should be in good shape, and what I would suggest is to just change the code to the following:
var productPrice = Convert.ToDecimal(gridView1.GetRowCellValue(
gridView1.FocusedRowHandle, "product_price"));
The only thing I omitted was the ToString(), so we can let the Convert function apply against the (raw) object. I don't know how or why, and it actually seems like a long shot, but maybe ToString() is formatting the output in accordance with the grid display.
I'm guessing that is not the case, and your original supposition is correct in that the data coming from MySQL is actually formatted as a string, or your C# code is reading it as a string. If this is the case, run the actual SQL and see what datatype is being rendered. Is it numeric? If so, is your C# reading it as numeric (reader.GetDecimal(x)) or, perhaps is there a reader.GetValue(x).ToString() that is ignoring datatypes?
In other words, is MySQL adding the formatting and sending a string, or is your C# changing a decimal to a string? Find out what's doing that and put a stop to it.
You can certainly unformat the string and then convert to a decimal, but that seems like a long, LONG path to your end goal.
In my application I use WpfLocalization to provide translations while the application is running. The library will basically maintain a list of properties and their assigned localization keywords and use DependencyObject.SetValue() to update their values when the active language is changed.
The scenario in which I noticed my problem is this: I have a simple TextBlock and have assigned a localization keyword for its Text property. Now when my application starts, it will write the initial value into it and it will display just fine on screen. Now I switch the language and the new value is set as the Text property but only half the text will actually display on screen. Switching the languages back and forth does not have any effect. The first language is always displayed fine, the second is cut off (in the middle of words, but always full characters).
The relative length of both languages to each other does not seem to have anything to do with it. In my test case the working language string is 498 bytes and the one that gets cut off is 439 bytes and gets cut off after 257 bytes).
When I inspect the current value of the Text property of said TextBlock right before I change its value through the localization code, it will always have the expected value (not cut off) in either language.
When inspecting the TextBlock at runtime through WPF Inspector it will display the cut off text as the Text property in the second language.
This makes no sense to me at all thus far. But now it gets better.
The original WpfLocalization library reads the localized strings from standard resource files, but we use a modified version that can also read those string from an Excel file. It does that by opening an OleDbConnection using the Microsoft OLE DB driver and reading the strings through that. In the debugger I can see that all the values are read just fine.
Now I was really surprised when a colleague found the fix for the "cut off text" issue. He re-ordered the rows in the Excel sheet. I don't see how that could be relevant, but switching between the two versions of that file has an impact on the issue.
That does actually make sense, it's because the ole db driver for Excel has to take a sample of the data in a column to assign it a type and in the case of string, also a length. If it only samples values below the 255 character threshold, you will get a string(255) type and truncated text, if it has sampled a longer string, it will assign it as a memo column and allow longer strings to be retrieved / stored. By re-ordering, you are changing which rows are sampled.
If you read the SQL Server to Excel using oledb you will find this is a known issue. http://msdn.microsoft.com/en-us/library/ms141683.aspx - since you are using the same ole db driver, I would expect the situation to also apply to you.
From the docs:
Truncated text.
When the driver determines that an Excel column
contains text data, the driver selects the data type (string or memo)
based on the longest value that it samples. If the driver does not
discover any values longer than 255 characters in the rows that it
samples, it treats the column as a 255-character string column instead
of a memo column. Therefore, values longer than 255 characters may be
truncated. To import data from a memo column without truncation, you
must make sure that the memo column in at least one of the sampled
rows contains a value longer than 255 characters, or you must increase
the number of rows sampled by the driver to include such a row. You
can increase the number of rows sampled by increasing the value of
TypeGuessRows under the
HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Jet\4.0\Engines\Excel registry
key. For more information, see PRB: Transfer of Data from Jet 4.0
OLEDB Source Fails w/ Error.
I have a brief discussion with my teammate regarding this. He says, if I enter a number in textbox, and try to use the value later on using textbox.text or val(textbox.text), I will not need to parse the value to integer. According to him, if the text attribute value is all number, you can directly get the value as integer, instead of string.
So, if I have textBox1.Text = "12345", then next time, if I use, intABC = textBox1.Text, it will not throw an error. Is it right? Does C# or other .Net language does this implicit conversion? Also, will the code store "12345" as string or integer? And how much memory will this value take, 5bytes for 5 characters or 2bytes for an integer?
TextBox.Text keeps the text as a simple string, it doesn't care about the real "meaning" of the string.
Then, if you want to have your number back, you need to parse the string, hence neither implicit nor explicit cast to int is allowed (or better, it will throw an exception if you do it...).
About the size, that text is stored as an UNICODE (UTF-16) string, hence from 2 to 4 bytes per character (depending on the character).
You can easily measure the size (just the size of the string, without the overhead due to reference size etc.) using the following code:
int numBytes = Encoding.Unicode.GetByteCount(stringToMeasure);
To find more info about strings, unicode and encodings have a look here, here or here .
your friend is wrong, it will make the compiler unhappy, the compiler won't even convert it automatically for you. Text property of a TextBox is of type string. check this
http://msdn.microsoft.com/en-us/library/system.web.ui.webcontrols.textbox.text.aspx
As to your question of other languages; if 'option strict' is not enabled, VB.NET will allow this. It will also allow this assignment if the input is not entirely numeric however, resulting in a runtime exception.
If you know you will only use numerical values, try using a NumericUpDown control.
You could then get/set the numerical value (decimal) by using the Value property.
A NumericUpDown control contains a single numeric value that can be incremented or decremented by clicking the up or down buttons of the control. The user can also enter in a value, unless the ReadOnly property is set to true.