error CS1525 why does it happen? - c#

I don't know why but when I'm trying to compile the next code I'm getting error CS1525 and every ) at the end of every while command is being marked as an error:
static void PrintArray(string[] arr)
{
int i, sum = 0, subb = 0, pow, x;
char opper;
Console.WriteLine("how many numbers does your calculation have?");
i = Convert.ToInt16(Console.ReadLine());
arr = new string[i];
for (i = 0; i < arr.Length; i++)
{
Console.WriteLine("enter num {0}" + i);
arr[i] = Console.ReadLine();
Console.WriteLine("arr[{0}] = {1}" + i, arr[i]);
}
Console.WriteLine("what do you want to do?");
opper = Convert.ToChar(Console.ReadLine());
while (opper = +)
{
for (i = 0; i < arr.Length; i++)
{
sum = sum + Convert.ToInt16(arr[i]);
}
Console.WriteLine("your sum is " + sum);
}
while (opper = -)
{
for (i = 0; i < arr.Length; i++)
{
subb = subb + Convert.ToInt16(arr[i]);
}
Console.WriteLine("your subb is" + subb);
}
while (opper = *)
{
pow = Convert.ToInt16(arr[0]);
for (i = 1; i < arr.Length; i++)
{
pow = pow * Convert.ToInt16(arr[i]);
}
Console.WriteLine("the resolt is " + pow);
}
while (opper = &)
{
x = Convert.ToInt16(arr[i]);
for (i = 0; i < arr.Length; i++)
{
x = x / Convert.ToInt16(arr[i]);
}
Console.WriteLine("your resolt is " + x);
}
Console.ReadKey();
}
I will be glad if someone can finally explain that to me...

Given the lines (for example)
opper = Convert.ToChar(Console.ReadLine());
while (opper = +)
It looks like you're trying to compare the character input to an operator. You'll want to change the assignment operator to a comparison operator, and compare the character to another character, like so:
opper = Convert.ToChar(Console.ReadLine());
while (opper == '+')

user1673882 is correct here about the cause of the compile error. However, there are several other significant bugs you should be aware of as well.
As for the original compile issue, you have two issues with the following line (and all similar lines);
while (opper = +)
First, = (single "equals" sign) is assignment, not comparison. You want to use == here instead.
Secondly, + is not a character in this case, it's an operation. (In fact, the compiler can't infer exactly which operator it might be).
Even if you get this to compile, though, it won't work because all of your loops are infinite loops. Consider this example:
char myChar = 'a';
// Infinite loop
while (myChar == 'a')
{
Console.WriteLine("Test");
}
How could this possibly get out of the loop, given that myChar will always be a?
A few other miscellaneous bugs follow:
subb = subb + Convert.ToInt16(arr[i]);
This could be shortened with
subb += Convert.ToInt16(arr[i]);
or possibly even
subb += (short)arr[i];
Also, I'm assuming this shouldn't be "+" since that's exactly the same operation you're doing if the operation is "+" (i.e. the outcome of "+" and "-" should be exactly the same).
x = x / Convert.ToInt16(arr[i]);
First, same cleanup as above:
x /= (short)arr[i];
Secondly, you never test for division by 0 here, so this might throw an exception.
Third, I'm not sure what type x is, but "short" is definitely not closed over division - i.e.:
short a = ...
short b...
// May not be another short
Console.WriteLine(a / b);
Actually, this applies to multiplication, subtraction, and addition to some extent too in this case since shorts have a finite size. Consider the following code:
short overflow = short.MaxValue;
// -32768
overflow++;
// +32767
overflow--;
// -32768 again
overflow++;
// -32767
overflow++;
checked
{
overflow = short.MaxValue;
// Now this results in an OverflowException
overflow++;
}
One more example:
short testArithmetic = 1;
// This gives us the result that 1 / 2 = 0.
testArithmetic /= 2;
// Set this back to 1 for the next operation
testArithmetic = 1;
// This is 0.0 too!
double testArithmeticFloat = testArithmetic / 2;
// This gives us the result we'd expect
testArithmeticFloat = 1.0 / 2.0;
// This'll compile just fine, but you get a DivideByZeroException when you try to execute it
testArithmetic /= 0;

Related

C# writing a program that input of 2 numbers (a and b),gives an output of the sum of squares in between

I`m quite new to the whole programming world.
And i started studying C#
i got the following exersice to do:
Write a program that upon the input of 2 numbers (a and b), u receive
an output of the sum of squares in between.
I.e. - The program receives a and b where b > a and calculates a^2
+ (a+1)^2 + (a+2)^2 + ... + (b-1)^2 + b^2.
E.g. - If a = 3 and b = 6, the output would be 86, since 3^2 +
4^2 + 5^2 + 6^2 = 9 + 16 + 25 + 36 = 86
But i don't have any idea where do i even begin.
I`m guessing i need some sort of loop within a loop maybe?
You need to use for loop for this. Please see below, if that helps-
int i, j, k;
int value=0;
Console.WriteLine("Enter the fist number ");
i = Convert.ToInt32(Console.ReadLine());
Console.WriteLine("Enter the second number ");
j = Convert.ToInt32(Console.ReadLine());
if (i > j)
{
Console.WriteLine("Second number should be greater then First");
Console.ReadLine();
Environment.Exit(0);
}
for (k = i; k <= j; k++)
{
value += k * k;
}
Console.WriteLine(value);
Console.ReadLine();
Perhaps a method that takes in two integers and returns a double is a good place to start (returning a double allows you to specify a wider range of numbers without getting inaccurate results):
public static double GetSumOfSquaresBetween(int first, int second)
{
}
Then you could implement the body by creating a loop that goes from the lowest number to the highest number, adding the square of the current number to a result, and then returning that result at the end.
Here's a Linq example that would most likely not be acceptable for this assignment but gives you the idea:
public static double GetSumOfSquaresBetween(int first, int second)
{
return Enumerable
.Range(Math.Min(first, second), Math.Abs(first - second) + 1)
.Select(number => Math.Pow(number, 2))
.Sum();
}
Try this
int a, b, sum = 0;
Console.WriteLine("Enter the fist number ");
a = Convert.ToInt32(Console.ReadLine());
Console.WriteLine("Enter the second number ");
b = Convert.ToInt32(Console.ReadLine());
if (a<b){
for (int x = a+1; x < b; x++)
{
sum += x * x;
}
Console.WriteLine(sum);
}
else{
Console.WriteLine("Wrong input!");
}
Console.ReadLine();
}
}
A for loop should do it.
double nTotal = 0;
for (int a = 3; a <= 6; a++)
{
nTotal += Math.Pow(a, 2);
}

Fast comparison of two doubles ignoring everything that comes after 6 decimal digits

I try to optimize the performance of some calculation process.
Decent amount of time is wasted on calculations like the following:
var isBigger = Math.Abs((long) (a * 1e6) / 1e6D) > ((long) ((b + c) * 1e6)) / 1e6D;
where "a","b" and "c" are doubles, "b" and "c" are positive, "a" might be negative.
isBigger should be true only if absolute value of "a" is bigger than "b+c" disregarding anything after the 6th decimal digit.
So I look at this expression, I understand what it does, but it seems hugely inefficient to me, since it multiplies and divides compared numbers by million just to get rig of anything after 6 decimal places.
Below is the program I used to try and create a better solution. So far I failed.
Can someone help me?
class Program
{
static void Main(string[] args)
{
var arrLength = 1000000;
var arr1 = GetArrayOf_A(arrLength);
var arr2 = GetArrayOf_B(arrLength);
var arr3 = GetArrayOf_C(arrLength);
var result1 = new bool[arrLength];
var result2 = new bool[arrLength];
var sw = new Stopwatch();
sw.Start();
for (var i = 0; i < arrLength; i++)
{
result1[i] = Math.Abs((long) (arr1[i] * 1e6) / 1e6D)
>
(long) ((arr2[i] + arr3[i]) * 1e6) / 1e6D;
}
sw.Stop();
var t1 = sw.Elapsed.TotalMilliseconds;
sw.Restart();
for (var i = 0; i < arrLength; i++)
{
//result2[i] = Math.Round(Math.Abs(arr1[i]) - (arr2[i] + arr3[i]),6) > 0; // Incorrect, example by index = 0
//result2[i] = Math.Abs(arr1[i]) - (arr2[i] + arr3[i]) > 0.000001; // Incorrect, example by index = 1
//result2[i] = Math.Abs(arr1[i]) - (arr2[i] + arr3[i]) > 0.0000001; // Incorrect, example by index = 2
result2[i] = Math.Abs(arr1[i]) - (arr2[i] + arr3[i]) > 0.00000001; // Incorrect, example by index = 3
}
sw.Stop();
var t2 = sw.Elapsed.TotalMilliseconds;
var areEquivalent = true;
for (var i = 0; i < arrLength; i++)
{
if (result1[i] == result2[i]) continue;
areEquivalent = false;
break;
}
Console.WriteLine($"Functions are equivalent : {areEquivalent}");
if (areEquivalent)
{
Console.WriteLine($"Current function total time: {t1}ms");
Console.WriteLine($"Equivalent function total time: {t2}ms");
}
Console.WriteLine("Press ANY key to quit . . .");
Console.ReadKey();
}
private static readonly Random _rand = new Random(DateTime.Now.Millisecond);
private const int NumberOfRepresentativeExamples = 4;
private static double[] GetArrayOf_A(int arrLength)
{
if(arrLength<=NumberOfRepresentativeExamples)
throw new ArgumentException($"{nameof(arrLength)} should be bigger than {NumberOfRepresentativeExamples}");
var arr = new double[arrLength];
// Representative numbers
arr[0] = 2.4486382579120365;
arr[1] = -1.1716818990000011;
arr[2] = 5.996414627393257;
arr[3] = 6.0740085822069;
// the rest is to build time statistics
FillTheRestOfArray(arr);
return arr;
}
private static double[] GetArrayOf_B(int arrLength)
{
if(arrLength<=NumberOfRepresentativeExamples)
throw new ArgumentException($"{nameof(arrLength)} should be bigger than {NumberOfRepresentativeExamples}");
var arr = new double[arrLength];
// Representative numbers
arr[0] = 2.057823225;
arr[1] = 0;
arr[2] = 2.057823225;
arr[3] = 2.060649901;
// the rest is to build time statistics
FillTheRestOfArray(arr);
return arr;
}
private static double[] GetArrayOf_C(int arrLength)
{
if(arrLength<=NumberOfRepresentativeExamples)
throw new ArgumentException($"{nameof(arrLength)} should be bigger than {NumberOfRepresentativeExamples}");
var arr = new double[arrLength];
// Representative numbers
arr[0] = 0.3908145999796302;
arr[1] = 1.1716809269999997;
arr[2] = 3.9385910820740282;
arr[3] = 4.0133582670728858;
// the rest is to build time statistics
FillTheRestOfArray(arr);
return arr;
}
private static void FillTheRestOfArray(double[] arr)
{
for (var i = NumberOfRepresentativeExamples; i < arr.Length; i++)
{
arr[i] = _rand.Next(0, 10) + _rand.NextDouble();
}
}
}
You don't need the division since if (x/100) < (y/100) that means that x<y.
for(var i = 0; i < arrLength; i++)
{
result2[i] = Math.Abs((long)(arr1[i] * 1e6))
> (long)((arr2[i] + arr3[i]) * 1e6);
}
with the results for me:
Arrays have 1000000 elements.
Functions are equivalent : True
Current function total time: 40.10ms 24.94 kflop
Equivalent function total time: 22.42ms 44.60 kflop
A speedup of 78.83 %
PS. Make sure you compare RELEASE versions of the binary which includes math optimizations.
PS2. The display code is
Console.WriteLine($"Arrays have {arrLength} elements.");
Console.WriteLine($"Functions are equivalent : {areEquivalent}");
Console.WriteLine($" Current function total time: {t1:F2}ms {arrLength/t1/1e3:F2} kflop");
Console.WriteLine($"Equivalent function total time: {t2:F2}ms {arrLength/t2/1e3:F2} kflop");
Console.WriteLine($"An speedup of {t1/t2-1:P2}");
Overall your question goes into the Area of Realtime Programming. Not nessesarily realtime constraint, but it goes into teh same optimisation territory. The kind where every last nanosecond has be shaved off.
.NET is not the ideal scenario for this kind of operation. Usually that thing is done in dedicated lanagauges. The next best thing is doing it in Assembler, C or native C++. .NET has additional features like the Garbage Collector and Just In Time compiler that make even getting reliable benchmark results tricky. Much less reliale runtime performance.
For the datatypes, Float should be about the fastest operation there is. For historical reasons float opeations have been optimized.
One of your comment mentions physics and you do have an array. And I see stuff like array[i] = array2[i] + array3[i]. So maybe this should be a matrix operation you run on the GPU instead? This kind of "huge paralellized array opeartions" is exactly what the GPU is good at. Exactly what drawing on the screen is at it's core.
Unless you tell us what you are actually doing here as sa operation, that is about the best answer I can give.
Is this what you're looking for?
Math.Abs(a) - (b + c) > 0.000001
or if you want to know if the difference is bigger (difference either way):
Math.Abs(Math.Abs(a) - (b + c)) > 0.000001
(I'm assuming you're not limiting to this precision because of speed but because of inherent floating point limited precision.)
In addition to asking this question on this site, I also asked a good friend of mine, and so far he provided the best answer. Here it is:
result2[i] = Math.Abs(arr1[i]) - (arr2[i] + arr3[i]) > 0.000001 ||
Math.Abs((long)(arr1[i] * 1e6)) > (long)((arr2[i] + arr3[i])*1e6);
I am happy to have such friends :)

Why do different algorithms of summing not match?

Assume that I want to get sum of all squares from M to N. I googled a bit and found this formula:
(1^2 + 2^2 + 3^2 + ... + N^2) = (N * (N + 1) * (2N + 1)) / 6
so I write this code:
static void Main(string[] args)
{
const int from = 10;
const int to = 50000;
Console.WriteLine(SumSquares(from, to));
Console.WriteLine(SumSquares2(from, to));
}
static long SumSquares(int m, int n)
{
checked
{
long x = m - 1;
long y = n;
return (((y*(y + 1)*(2*y + 1)) - (x*(x + 1)*(2*x + 1)))/6);
}
}
static long SumSquares2(int m, int n)
{
long sum = 0;
for (int i = m; i <= n; ++i)
{
sum += i * i;
}
return sum;
}
it works fine until 40k, but when N becomes 50k it fails. Output for 50k:
41667916674715
25948336371355
Press any key to continue . . .
I think it's an overflow or something, so I added checked keyword and tried to change long to double, but I got the same result. How can it be explained? How to get correct result without loops?
Your second method is overflowing because you are using an int in the loop. Change it to a long as follows (and also add checked):
static long SumSquares2(int m, int n)
{
checked
{
long sum = 0;
for (long i = m; i <= n; ++i)
{
sum += i*i;
}
return sum;
}
}
What was going wrong is that i*i was being calculated internally as an int data type even though the result was being cast to a long data type (i.e. the variable sum), and so it overflowed.
While you are using long for the result, you are still using int for the operators. I would define M and N as long or even BigInteger, and the same for the result. If you do not, you are probably doing int arithmetic still, even though your result is of type long.
I tried your code, and got the results you got. But then I changed every int to long and got the two numbers to match, up to an N of 1600000.
Using BigInteger, I am up to 160000000 and still working ok (result for m=10 and n=160000000 is 13653333461333333359999715, both ways).
To use BigInteger, you will need to add a reference to the System.Numerics dll to your project, and you will need to have a statement at the top of your code including that library.
using System.Numerics;
namespace ConsoleFiddle
{
class Program
{
static void Main(string[] args)
{
BigInteger from = 10;
BigInteger to = 160000000;
Console.WriteLine(SumSquares(from, to));
Console.WriteLine(SumSquares2(from, to));
Console.ReadKey();
}
static BigInteger SumSquares(BigInteger m, BigInteger n)
{
checked
{
BigInteger x = m - 1;
BigInteger y = n;
return (((y * (y + 1) * (2 * y + 1)) - (x * (x + 1) * (2 * x + 1))) / 6);
}
}
static BigInteger SumSquares2(BigInteger m, BigInteger n)
{
checked
{
BigInteger sum = 0;
for (BigInteger i = m; i <= n; ++i)
{
sum += i * i;
}
return sum;
}
}
For an M of 4000000000000000000 (4 x 10^18), and an N of 4000000000100000000. This code still works and gives an immediate result with the first method (1600000016040000000400333333338333333350000000). With the second method it takes it a little while (100 million loop iterations) but gives the same result.
Most probably you are experiencing integer overflow, as the range of long is limited. Probably you have disabled exceptions for integer overflow, so no exception is thrown. The exceptions for integer overflow can be disabled and enabled in the project properties in Visual Studio, if I'm not mistaken.

how do I print a number less than 1 but greater than 0?

I am expressing the power method in a script, at one point I am trying to do a negative, which is 1 / final_answer
the thing is it does not print things such as 2^-3 which is .125
using System;
class MainClass
{
static void Main()
{
Console.Write ("Enter a base number: ");
string str_x = Console.ReadLine ();
double x = double.Parse (str_x);
Console.Write ("Enter an exponent: ");
string str_n = Console.ReadLine ();
double n = double.Parse (str_n);
double final = 1;
int count = 1;
while (count != n+1) {
final = final * x;
count++;
}
if (n < 0)
final = 1 / final;
Console.WriteLine(final);
}
}
First of all, the loop
int count = 1;
while (count != n + 1)
final = final * x;
count++;
}
cannot end if n == -3 since count is always positive.
In addition, it could be an endless loop because you compare int and double
double n = float.Parse (str_n);
....
int count = 1;
while (count != n + 1) {
You should avoid use of == and != with doubles.
With negative values of the exponent, your loop never terminates because count will never reach a negative value (or zero), at least until it overflows.
And as others said, read the exponent as an integer, not a double.

Determine if all digits of the sum of n and swapped n are odd

I need to determine if all the digits of the sum of n numbers and swapped n are odd.
For example:
36 + 63 = 99 (9 and 9 are both odd)
409 + 904 = 1313 (1 and 3 are both odd)
Visual Studio builds my code and it runs, but it doesn't return an answer.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
long num = Convert.ToInt64(Console.Read());
long vol = voltea(num);
long sum = num + vol;
bool simp = simpares(sum);
if (simp == true)
Console.Write("Si");
else
Console.Write("No");
}
static private bool simpares(long x)
{
bool s = false;
long [] arreglo = new long [1000];
while ( x > 0)
{
arreglo [x % 10] ++;
x /=10;
}
for (long i=0 ; i <= arreglo.Length ; i++)
{
if (arreglo [i]%2 != 0)
s = true;
}
return s;
}
static private long voltea(long x)
{
long v = 0;
while (v > 0)
{
v = 10 * v + x % 10;
x /= 10;
}
return v;
}
}
}
I'm not sure what's wrong with your code, but I was thinking an easier way to accomplish this would be to use strings, rather than doing all the divisions and mods by 10.
Convert original number to string, reverse the string, then convert that back to a long
Add the original and reversed numbers
Convert the sum to a string
Loop over the result string and check to see if each digit is odd
It's not too clear what you mean by "Doesn't return an answer".
Add:
Console.ReadKey();
Console.ReadLine();
At the end of your Main function. I'd hazard a guess that you're not seeing an answer because the console is closing on you.
EDIT:
Found it:
for (long i=0 ; i <= arreglo.Length ; i++)
Index out of bounds. That should be:
for (long i=0 ; i < arreglo.Length ; i++)
i should be "Less than" arreglo, not "Less than or equal to"
EDIT2:
This is why your current code is broken. I'd highly recommend also looking at alternative methods of solving the problem. See Andy White's Answer.
It looks to me like you might have an infinite loop and a loop that never enters.
// because v = 0, the while will never execute
long v = 0;
while (v > 0)
{
v = 10 * v + x % 10;
x /= 10;
}

Categories