The problem of my code is if I put value in pay money(textbox) and I turned to zero giving me an error
System.FormatException: 'Input string was not in a correct format.'
This is my code :
private void txtPM_TextChanged(object sender, EventArgs e)
{
string fee = lblFee.Text.Trim();
string pm = txtPM.Text.Trim();
int number = Convert.ToInt32(fee);
int number2 = Convert.ToInt32(pm);
int minus = number2 - number;
txtChange.Text = minus.ToString().Trim();
}
I will put here the form
I hope you can help me thanks guys
You may need Convert.ToDecimal() if you are working with monetary values specified as decimals. (I second the empty and null checking suggestions)
Update for clarification:
Currently, you are converting string to Int32 with the following:
int number = Convert.ToInt32(fee);
int number2 = Convert.ToInt32(pm);
You can instead convert to decimal with the following:
decimal number = Convert.ToDecimal(fee);
decimal number2 = Convert.ToDecimal(pm);
Update2 (full method updated with null and empty checks):
private void txtPM_TextChanged(object sender, EventArgs e)
{
string fee = lblFee.Text.Trim();
string pm = txtPM.Text.Trim();
decimal number = 0;
decimal number2 = 0;
if(!string.IsNullOrWhiteSpace(fee)) number = Convert.ToDecimal(fee);
if(!string.IsNullOrWhiteSpace(pm)) number2 = Convert.ToDecimal(pm);
decimal minus = number2 - number;
txtChange.Text = minus.ToString().Trim();
}
Use the decimal type because it's more appropriate for financial and monetary calculations. To avoid the exception use decimal.TryParse. If the strings pm and fee are not in the right format decimal.TryParse will return zero and no exception will be thrown. You can also remove the Trim() on the last line.
private void txtPM_TextChanged(object sender, EventArgs e)
{
string fee = lblFee.Text.Trim();
string pm = txtPM.Text.Trim();
decimal number;
decimal.TryParse(fee, out number);
decimal number2;
decimal.TryParse(pm, out number2);
decimal minus = number2 - number;
txtChange.Text = minus.ToString();
}
You can use TryParse as already pointed out in the duplicate.
Also it makes more sense to use decimal when working with monetary values.
private void txtPM_TextChanged(object sender, EventArgs e)
{
decimal.TryParse(lblFee.Text, out decimal number);
decimal.TryParse(txtPM.Text, out decimal number2);
txtChange.Text = (number2 - number).ToString();
}
When using C# 6.0 or earlier you have to declare the variables in a separate statement:
private void txtPM_TextChanged(object sender, EventArgs e)
{
decimal number;
decimal.TryParse(lblFee.Text, out number);
decimal number2;
decimal.TryParse(txtPM.Text, out number2);
txtChange.Text = (number2 - number).ToString();
}
Related
I need parse the list of nums with a point in the thousand in c# .
The 3.7 to 3700
The 6.45 to 6450
and if I need 5432.2 pass to 5432200 same
Tanks
Just parse as decimal and multiply by 1000.
Parse the value as a decimal (specifying the correct culture) and multiply it with 1000.
private void button1_Click(object sender, EventArgs e)
{
string s = "5432.2";
if(TryParseToPermille(s, CultureInfo.InvariantCulture, out int promille))
{
MessageBox.Show(promille.ToString());
}
}
Using CultureInfo.InvariantCulture will always interprete the dot as decimal separator and commas as thousand separators. If you want to use the current user's culture, use CultureInfo.CurrentCulture instead.
public static bool TryParseToPermille(string input, IFormatProvider formatProvider, out int promille)
{
bool result = false;
promille = 0;
if(Decimal.TryParse(input, NumberStyles.Number, formatProvider, out decimal value))
{
result = true;
value = value * 1000;
promille = (int)Math.Truncate(value); // or "Round" or "Ceiling" or "Floor" depending on your use case
}
return result;
}
public static bool TryParseToPermille(string input, out int promille)
{
return TryParseToPromille(input, CultureInfo.CurrentCulture, out promille);
}
multiple by 1000 and convert into int
double num1 = 3.7;
double num2 = 6.45;
int num1_convert = Convert.ToInt32(num1 * 1000);
int num2_convert = Convert.ToInt32(num2 * 1000);
Result :
3700
6450
In my program I am using a database containing a Time (string previousTimeVASN).
I have a timer to clock total seconds. i would like to display the sum of previousTimeVASN + the total seconds.
I have error showing:
"System.FormatException: 'Input string was not in a correct format.'" at line: double test1 = Convert.ToDouble(previousTimeVASN);
any suggestion are much appreicated.
private void sNbtn_Click(object sender, RoutedEventArgs e)
{
TabControl.SelectedIndex = 1;
dtVASN.Tick += new EventHandler(dtVASN_Tick);
dtVASN.Interval = new TimeSpan(0, 0, 0, 0, 1);
}
void dtVASN_Tick(object sender, EventArgs e)
{
if (swVASN.IsRunning)
{
TimeSpan tsVASN = swVASN.Elapsed;
double test = tsVASN.TotalSeconds;
double test1 = Convert.ToDouble(previousTimeVASN);
txtVASN.Text = (test + test1).ToString();
}
}
The method Convert.ToDouble will throw FormatException if value is not a number in a valid format. You are getting the same here means either the value in previousTimeVASN is not a number or it is not in the expected format. Here is an alternate option for you to check whether the conversion is possible or not, that is, Double.TryParse Method
Converts the string representation of a number in a specified style
and culture-specific format to its double-precision floating-point
number equivalent. A return value indicates whether the conversion
succeeded or failed.
So the code can be revamped as like the following:
if (swVASN.IsRunning)
{
TimeSpan tsVASN = swVASN.Elapsed;
double test = tsVASN.TotalSeconds;
double test1;
Double.TryParse(previousTimeVASN, out test1);
txtVASN.Text = (test + test1).ToString();
}
if you want to alert the user that the second number is not valid then you can use the return value of parse like the following:
if(Double.TryParse(previousTimeVASN, out test1))
txtVASN.Text = (test + test1).ToString();
else
txtVASN.Text = "previous Time VASN is not valid:'
Screenshot of the Form First time poster, and im in need of some help here. I am working on a program that calculates an athletes salary after hiring agents, lawyers, agents, etc. I have a listbox that displays the salary*the constant percentage of the agent. I CANNOT seem to get the sum of the numbers entered so i can subtract them from the total salary and display it in a label. I would love some help, very new to C#.
The area in question is commented out under the Switch
public partial class athleteForm : Form
{
public athleteForm()
{
InitializeComponent();
}
const decimal LAWYER_PERCENT = 0.10m;
const decimal AGENT_PERCENT = 0.05m;
const decimal PA_PERCENT = 0.03m;
const decimal TRAINER_PERCENT = 0.07m;
const string LAWYER_STRING = "Lawyer";
const string AGENT_STRING = "Agent";
const string PA_STRING = "Personal Assistant";
const string TRAINER_STRING = "Trainer";
string profFirstName;
string profLastName;
string profSelect;
decimal profPay;
public void athleteForm_Load(object sender, EventArgs e)
{
}
public void profAddButton_Click(object sender, EventArgs e)
{
decimal startingSalary = Convert.ToDecimal(startingSalaryText.Text);
profFirstName = profFirstNameText.Text;
profLastName = profLastNameText.Text;
profSelect = profComboBox.GetItemText(profComboBox.SelectedItem);
decimal lawyerPay = startingSalary * LAWYER_PERCENT;
decimal agentPay = startingSalary * AGENT_PERCENT;
decimal trainerPay = startingSalary * TRAINER_PERCENT;
decimal paPay = startingSalary * PA_PERCENT;
switch (profComboBox.GetItemText(profComboBox.SelectedItem))
{
case "Lawyer":
profPay = lawyerPay;
break;
case "Agent":
profPay = agentPay;
break;
case "Trainer":
profPay = trainerPay;
break;
case "Personal Assistant":
profPay = paPay;
break;
}
profListBox.Items.Add(profFirstName + " " + profLastName + " " + profSelect);
profPayList.Items.Add("$ " + profPay);
//decimal sumOfListbox =
// (from string S in profPayList.Items
// select Convert.ToDecimal(S))
// .Sum();
decimal sum =
profPayList.Items
.Cast<string>()
.Sum(v =>
{
decimal d;
return decimal.TryParse(v, out d) ? d : 0m;
});
remainSalaryLabel.Text = (sum.ToString());
}
public void clearButton_Click(object sender, EventArgs e)
{
switch (MessageBox.Show("Are you sure you want to clear all professionals?",
"WonderWord",
MessageBoxButtons.YesNoCancel,
MessageBoxIcon.Question))
{
case DialogResult.Yes:
profListBox.Items.Clear();
profPayList.Items.Clear();
remainSalaryLabel.Text = " ";
break;
case DialogResult.No:
// "No" processing
break;
case DialogResult.Cancel:
// "Cancel" processing
break;
}
}
}
}
The problem is that you are storing your data as a string prefixed with a dollar sign ($). e.g. "$5";
When your are calculating the sum of all of your data, you are correctly using a decimal.TryParse to convert the string to a decimal. However, in this case, the TryParse will not succeed in extracting the number due to the dollar sign.
Therefore, your options for fix this are:
Remove the dollar sign before parsing;
Use the Decimal.TryParse overload that handles numberstyles and currency symbols;
Maintain a separate list of numbers to sum instead of storing them within the ListBox so you don't have to deal with the dollar sign. If you wish to still display the numbers, you can still bind the list of numbers to the ListBox and update whenever a new number is added.
Option 2 would be your best option for the current state of your code. Assuming you're dealing with US culture, your code will need to look similar to this:
NumberStyles style = NumberStyles.Number | NumberStyles.AllowCurrencySymbol;
CultureInfo culture = CultureInfo.CreateSpecificCulture("en-US");
decimal sum = profPayList.Items
.Cast<string>()
.Sum(v =>
{
decimal d;
return decimal.TryParse(v, style, culture, out d) ? d : 0m;
});
Option 3 is what I would be going with if you have time to rewrite what you have as it will solve some other potentially issues with your code that could arise in the future.
I am having an issue with rounding on a c# Payroll program.
I tested it with 15.50 hourly rate x 39.75 hours. This comes to $616.125 gross pay, rounded up to $616.13 gross.
Then I did a fixed Income tax of 25%, which means the final Net Pay of (15.50 x 39.75) x .25 = 462.10
However it keeps displaying a Net Pay of 462.09, so it must not be using the rounded gross pay for the display part. The Gross Pay and Income tax are displaying correctly
Here is all of the code, my guess is that this line needs to be changed among others:
decimal incomeTax = Math.Round(grossPay, 3) * taxRate;
Any ideas what I need to do to get it to round correctly?
decimal hourlyRate = 0;
decimal hoursWorked = 0;
decimal grossPay = 0m;
decimal incomeTax = 0m;
decimal netPay = 0m;
decimal taxRate = .25m;
private void btnCalculate_Click(object sender, EventArgs e)
{
decimal hourlyRate = Convert.ToDecimal(txtHourlyRate.Text);
decimal hoursWorked = Convert.ToDecimal(txtHoursWorked.Text);
decimal grossPay = Math.Round(hourlyRate * hoursWorked, 3);
decimal incomeTax = Math.Round(grossPay, 3) * taxRate;
decimal netPay = grossPay - incomeTax;
txtGrossPay.Text = grossPay.ToString("c");
txtIncomeTax.Text = incomeTax.ToString("c");
txtNetPay.Text = netPay.ToString("c");
}
private void btnClear_Click(object sender, EventArgs e)
{
hourlyRate = 0;
hoursWorked = 0;
grossPay = 0m;
incomeTax = 0m;
netPay = 0m;
txtHourlyRate.Text = "";
txtHoursWorked.Text = "";
txtGrossPay.Text = "";
txtIncomeTax.Text = "";
txtNetPay.Text = "";
}
private void btnExit_Click(object sender, EventArgs e)
{
this.Close();
}
616.125 undergoes midpoint rounding. decimal uses banker's rounding by default. So (and this is something you can check yourself very easily if you just step through your code):
Math.Round(616.125M, 2) // 616.12M
Of course, you're also rounding to three decimal places, so you're actually getting 616.125M instead of 616.12M (or 616.13M) anyway.
You're doing something quite dangerous - you're guessing around tax calculations. Don't do that. Find the applicable tax laws - they will have the exact method used for calculating taxes. Follow those to a T. They specify where and when and how you should round anything. Most likely, all rounding (except for the final price/tax) is supposed to be done to four decimal places, not two, but again, don't guess - read the laws, and make sure you understand them perfectly.
decimal grossPay = Math.Round(hourlyRate * hoursWorked, 3);
returns 616.125, for which the rest of the calculations correctly lead to 462.09.....
It should be
decimal grossPay = Math.Round(hourlyRate * hoursWorked, 2, MidpointRounding.AwayFromZero);
Note the second parameter, the decimal place to round to, is 2 instead of 3, and the MidpointRounding parameter which will round 616.125 to 616.13 and get the result you expect.
private void txtFinal_Leave_1(object sender, EventArgs e)
{
int prelim;
int midterm;
int final;
decimal average;
string remarks;
prelim = int.Parse(txtPrelim.Text);
midterm = int.Parse(txtMidterm.Text);
final = int.Parse(txtFinal.Text);
average = (prelim + midterm + final) / 3;
txtAverage.Text = average.ToString();
if (average >= 75)
{
remarks = "passed";
}
else
{
remarks = "failed";
}
txtRemarks.Text = remarks;
// this is the output 83 passed
// I want to be like this 83.25 passed
}
average = (prelim + midterm + final) / 3.0m;
This will fix your problem.
Int is an integer type; dividing two ints performs an integer division, i.e. the fractional part is truncated since it can't be stored in the result type (also int!). Decimal, by contrast, has got a fractional part. By invoking Decimal.Divide, your int arguments get implicitly converted to Decimals.
You can enforce non-integer division on int arguments by explicitly casting at least one of the arguments to a floating-point type, e.g.: 3.0m this is casting to decimal !
please upgrade your code as follow:
average = Convert.ToDecimal(prelim + midterm + final) / 3;
txtAverage.Text = string.Format("{0:0.00}", average);