sql type float, real, decimal? - c#

well in my database i had a colum for price of one product
i had it as float, my problem is if i saved it since my c# application
as 10.50 .. in a query it returns 10,50 and if i update i get a error
10,50 cant convert to float ... or something so..
and if i saved it as decimal, in queries inside sql management .. are ok..
but in my c# application... i get the same error..
10.50 retuns as 10,50 i dont know why, and how to solved it.. my unique solution is saved it
as varchar...

That's a localisation problem of some sort. 10,50 is the "European" way of writing ten and a half. If you're getting that from your select statements then your database is probably configured incorrectly.

Generally speaking you should use the same type throughout your layers. So if the underlying types in the database are x, you should pass around those data with identical types in c#, too.
What type you choose depends on what you are storing--you shouldn't be switching around types just to get something to "work". To that end, storing numeric data in a non-numeric type (e.g. varchar) will come back to bite you very soon. It's good you've opened this question to fix that!
As others have miraculously inferred, you are likely running into a localization issue. This is a great example of why storing numbers as strings is a problem. If you properly accept user input in whatever culture/localization they want (or you want), and get it into a numeric-type variable, then the rest (talking to the DB) should be easy. More so, you should not do number formatting in the database if you can help it--that stuff is much better placed at the front end, closer to the users.

I think your setting in windows regional and language for decimal symbol is wrong.please set it to dot and again test it.

This may help out for temporary use but I wouldn't recommend it for permanent use:
Try making it so that just before you save the file, convert the number to a string, replace the commas with periods (From , to .) and then save it into the database as the string, hopefully it should see that it is in the correct format and turn it into what the database sees as "Decimal" or "Floating".
Hope this helps.

Yep, localization.
That said, I think your pice is being stored on a "money" field in SQLServer (I'm assuming it's SQLServer you're using). If that was a float in the DB, it would return it with a normal decimal point, and not the European money separator ",".
To fix:
Fist DO NO USE FLOAT in your c# code, unless you absolutely require a floating point number. Use the decimal type instead. That's not just in this case, but in all cases. Floating point numbers are binary (base-2), not decimal (base-10), so what you see in the interface is only a decimal approximation of the actual number. The result is that frequently (1 == 1) evaluates as false!
I've run into that problem myself, and it's maddening if you don't know that can happen. Always use decimal instead of float in c#.
Ok, after you've fixed that, then do this to get the right localization:
using System.Globalization;
...
NumberFormatInfo ni = new NumberFormatInfo();
ni.CurrencyDecimalSeparator = ",";
decimal price = decimal.Parse(dbPriceDataField, ni);
Note that "dbPriceDataField" must be a string, so you may have to do a ".ToString()" on that db resultset's field.
If you end up having to handle other "money" aspects of that money field, like currency symbols, check out: http://msdn.microsoft.com/en-us/library/system.globalization.numberformatinfo.aspx
If you need more robust error handling, either put that decimal.Parse in a try/catch, or use decimal.TryParse.
EDIT --
If you know what culture (really, country), the db is set to, you can do this instead:
using System.Globalization;
...
CultureInfo ci = new CultureInfo("fr-FR"); // fr-FR being "french France"
decimal price = decimal.Parse(dbprice, ci.NumberFormat);

Such problems were faced by me in my Web Apps... but i found the solution like I was fetching my price value in textbox. So I was have database attached with that. So when you attached your database with textbox... When you right click textbox and click Edit DataBinding.... in that you have to provide.... type like in Bind Property..... {0:N2}
This will work only for web apps or websites... not for desktop applications...

Related

C#/ClosedXML: problem with reading long numbers as text

I have a table with account numbers in one column and I need to read it. Some of them are read just fine, but some are treated as numbers and either converted into a scientific notation or wrong if I change the format to "0"
For example this dummy account :
is read as
after changing the format to "#".
If I don't change it, it's wrong:
which, obviously is a completely random account number then.
I've searched for and tried out different options, but none is working.
Any idea? Thank you
Account numbers aren't real numbers. You're never going to perform mathematical operations on them. You're better off treating them as text. Use cell.SetValue(value.ToString()).

Units conversion - Problem on re-converting rounded-off results back to original units

Checked all questions in SO that seemed related to my problem but could not find any answer that helps in my scenario.
I am developing an Asp.Net MVC 5 application with razor views and SQL Server as the database. I have a requirement to convert values from English to Metric units and back (Inches to Millimeter and back, Horsepower to Kilowatt and back etc.) on the go while user types in one of the unit value fields.
I achieve it by using UnitsNet conversion functions through ajax calls from UI on jQuery keyup events of the input fields. This works fine when user types in the values, and the converted values appears with several decimal points.
For example, 470 Hp (Horsepower) = 345.6844125 Kw (Kilowatts), and it correctly converts back to Hp.
However, when the values are rounded off, the conversion back to original value gives different result since the conversion happens on the rounded value.
I.e., 470 Hp = 345.68 Kw. And when converting back to Hp, it comes as: 345.68 Kw = 469.99 Hp.
The same happens when saving the values into database also. The column that saves the value is decimal (8,2) which obviously rounds off the values and gives this same results.
I would like to know your opinions on what would be the best way to handle this, to show consistent values on screen while converting and re-converting the values. Keeping all fields non-rounded, and also allowing maximum decimal points in the database minimizes this issue, but I am not sure if it is the correct way of handling this. Any help is appreciated.

How to format currency from database

The goal
I want to format correctly the currency from database.
The problem
I'm formatting the currency from database with this:
#String.Format("{0:C}", #Model["MinProductPrice"])
The problem is: 150 have to be 1,50, and not 150,00 — and this formatting is doing this.
What is the right formatting type to my case?
You probably want to divide the number by 100 first (remember to change the type), so 150 becomes 1.50, which gets converted to "1,50" depending on locale:
#String.Format("{0:C}", #Model["MinProductPrice"] / 100.0m)
I'll extend my comments into an answer, I think that's more appropriate. I think you should change the column type to a money or decimal type to prevent bugs by making the use of the column more obvious. Your output on your page will be correct and won't require any "magic numbers" to get it to print out properly.
Just a note but you can also print a currency string doing this:
#Model["MinProductPrice"].ToString("C")
I attributed the casting responsibility to database. I'm using MySQL and the query is like this:
ROUND(CAST(MIN(`map`.`Product_Price`) AS DECIMAL)/100,2) as `minProductPrice`
Anyway, I would to thanks jlafay and csharpler about their answers — they were very helpful and worked well for me.

Convert from British coordinates to standard WGS84 nmea

I was posting similar post already. And I did get an answer in theory but I really need somone to help me.
So I am using this EXAMPLE for testing my GPS. What I want to do is how to get standard decimal values like 56,322415 for latitude and longitude.
Because now I am getting 5304,254 value.
I need it in this form because I will use this for Google maps.
Can you check code and tell me what should I left out or how to convert it to WGS84 format.
Thank you.
EDIT:
Here is the picture that is explaining what I see when I run the program
And this is the one that is one the codeproject page:
EDIT 2:
So when I use THIS CONVERTER to see what decimal values I need to get when I have degrees I don't get the same values.
This is the value that I should get :
And this is the value that I get in the program:
46.64662666666667
Any idea why I can't get same conversion?
the following line in the ParseNMEA function is the one that does the conversion from WGS84 to the British Ordinance Survey coordinates:
return Transform(deciLat, deciLon, height);
so if you remove that line and just use deciLat and deciLon values, you should be fine...
Addition after question update:
The code you're referring to does not take local number formats into account, so if this goes wrong, it might be because of erroneous decimal symbol matching.
You can use the following functions to do the conversion, presuming the input is always in the invariant culture (with decimal points):
string[] arrLon = strLon.Split(new char[]{'°', '"'}, StringSplitOptions.RemoveEmptyEntries);
double dblLon = double.Parse(arrLon[0]) + double.Parse(arrLon[1], new System.Globalization.NumberFormatInfo()) / 60;
double deciLon = arrLon[2] == "E" ? dblLon : - dblLon;
Additional info:
NumberFormatInfo: http://msdn.microsoft.com/en-us/library/system.globalization.numberformatinfo.aspx
It sounds like your problems are now solved, I do know that there were issues caused by different local number formatting which were raised and resolved in one of the comments:
http://www.codeproject.com/Articles/13577/GPS-Deriving-British-Ordnance-Survey-Grid-Referenc?msg=2106791#xx2106791xx
If you simply want decimal values for lat and lon, I guess you can throw the entire thing away now and just use the solution provided by Dirk! =o)
Alex

Suggest a good method for having a number with high precision in C#

I am programming on a project which I should store the key of the user to the initial configuration of a machine, I want to write it in C#.
I have an initial configuration which consists of two number R and X0, R = 3.9988 and X0 = 0.5. I want to add the user key to these numbers. for example:
Key: hos110 =>
R = 3.9988104111115049049048
X0 = 0.5104111115049049048
104111115049049048 are ASCII codes of the key which are concatenated.
How can I store these numbers?
Is there a better method for doing this?
Update: How about MATLAB?
You're not really "adding" numbers. You are concatenating strings.
Store them as strings. You can't get much more precise than that.
If you need to perform any arithmetic operations, it is easy enough to convert them to a decimal number on the fly.
I don't really follow why you're using a key as part of a number, but leaving that aside... System.Decimal (aka decimal) seems like the right tool for the job here.
If you need infinite precision you need something that is called BigInteger. However these classes are usually only used for scientific calculations (and usually unsuited for stroring the data) which doesn't really seem to match your code sample. If you need to do only general calculations use Strings and then convert them to Decimal for the calculations.
However if you are looking for such a BigInterger Class you can find one here.
.Net 4.0 will have a BigInteger built-in-class in the class libraries named System.Numerics.BigInteger.
Well, depending on the precision you are trying to achieve, you can probably save these as a pair of decimal values.
However, if this is an ASCII code, you may just want to save these as a string directly. This will avoid the numerical precision issues, especially if you're going to pull off the 104111... prior to using this information.
It seems that you are storing a "key", so why not use a String then?
Floating point numbers are inherently imprecise. I'm not sure what this 'initial configuration' is or why it's a float, but you're not going to be able to tack on a 'user key' (whatever that may be) and recover it later. Store the user key separately, in a string or something.
If these 'numbers' have no numeric value, i.e. you will not use them for mathematical computation then there is no need to store them in a numeric datatype. You can store them as strings.

Categories