I'm trying to display the prime factors of a number. The code works, but I'm struggling with the unit test, as I'm not as familiar with it (I have to return a string in method).
public class PrimeFactor
{
static void Main(string[] args)
{
int userInput;
Console.Write("Please enter a number to find its prime factors: ");
userInput = Int32.Parse(Console.ReadLine());
PrimeFactors(userInput);
Console.ReadLine();
}
public static string PrimeFactors(int number)
{
Console.Write($"Prime Factors of {number} are: ");
// Even Numbers
while(number % 2 == 0)
{
Console.Write("2 ");
number = number / 2;
}
// Odd Numbers
for (int i = 3; i <= Math.Sqrt(number); i += 2)
{
while (number % i == 0)
{
Console.Write($"{i} ");
number = number / i;
}
}
if (number > 2)
{
Console.Write($"{number} ");
}
return number.ToString();
}
}
The code above, displays the prime factors, but when doing the unit test, it keeps failing and the actual is not providing the right output.
[TestClass]
public class UnitTest1
{
[TestMethod]
public void TestMethod1()
{
// Arrange
string expected = "2 2 2 5 ";
// Act
string actual = PrimeFactor.PrimeFactors(40);
// Asset
Assert.AreEqual(expected, actual);
}
}
When running the test, its displaying the actual as 5. I'm not sure what's happening.
You are returning the last prime factor (in your case "5"), not the string you expect. Instead of putting it into the console, return it from the function, like so:
public class PrimeFactor
{
static void Main(string[] args)
{
int userInput;
Console.Write("Please enter a number to find its prime factors: ");
userInput = Int32.Parse(Console.ReadLine());
Console.Write($"Prime Factors of {userInput} are: ");
string primeFactors = PrimeFactors(userInput);
Console.Write(primeFactors);
}
public static string PrimeFactors(int number)
{
string result = "";
// Even Numbers
while(number % 2 == 0)
{
result += "2 ";
number = number / 2;
}
// Odd Numbers
for (int i = 3; i <= Math.Sqrt(number); i += 2)
{
while (number % i == 0)
{
result += $"{i} ";
number = number / i;
}
}
if (number > 2)
{
result += $"{number} ";
}
return result;
}
}
With this shape of the function, you can easily unit test it with the code you wrote.
If you care about memory-optimisation, you can replace string concatenation with StringBuilder.
Related
why does my code not calculate an average score when entering "-1" into the console? It comes up at 0. It's a part of a loop exercise, so I'm sure there are faster ways to code this. I want to fix it within my current C# comprehension.
Here's the task
using System;
namespace Challenge_Loops1
{
internal class Program
{
static void Main(string[] args)
{
string individualScore = "0";
int scoreCount = 0;
int totalScore = 0;
int individualScoreIntoInt = 0;
while (individualScore != "-1")
{
Console.WriteLine($"Last number was {individualScoreIntoInt}");
Console.WriteLine("Please enter the next score");
Console.WriteLine($"Current amount of entries: {scoreCount}");
Console.WriteLine("Enter '-1' when you're ready to calculaate the average");
individualScore = Console.ReadLine();
if (individualScore.Equals("-1"))
{
Console.WriteLine("--------------------------------------------");
double averageScore = (double)totalScore / (double)scoreCount;
Console.WriteLine($"The average total score is {averageScore}");
if(int.TryParse(individualScore, out individualScoreIntoInt) && individualScoreIntoInt > 0 && individualScoreIntoInt < 21)
{
totalScore += individualScoreIntoInt;
//longer way: totalScore = individualScoreIntoInt + totalScore;
}
else if(individualScoreIntoInt < 0 || individualScoreIntoInt < 20)
{
Console.WriteLine("Enter a score > 0 and < 21");
continue;
}
else
{
Console.WriteLine("Please only enter numbers");
}
}
scoreCount++; // adding the individualscore entered to the count. writing it here so that it's only
//added to the count if it meets the requirements
}
}
}
}
Order of operations was incorrect:
1st validate if it's -1 or not,
2nd parse value and if it's possible perform below operations, if not drop error.
This was logic issue, rather than code itself.
You had added iteration despite exceptions, you didn't include possibility of 21 etc.
namespace Challenge_Loops1
{
internal class Program
{
static void Main(string[] args)
{
string individualScore = "0";
int scoreCount = 0;
int totalScore = 0;
int individualScoreIntoInt = 0;
while (individualScore != "-1")
{
Console.WriteLine($"Last number was {individualScoreIntoInt}");
Console.WriteLine("Please enter the next score");
Console.WriteLine($"Current amount of entries: {scoreCount}");
Console.WriteLine("Enter '-1' when you're ready to calculaate the average");
individualScore = Console.ReadLine();
if (individualScore.Equals("-1"))
{
Console.WriteLine("--------------------------------------------");
double averageScore = (double)totalScore / (double)scoreCount;
Console.WriteLine($"The average total score is {averageScore}");
}
else if (int.TryParse(individualScore, out individualScoreIntoInt))
{
if(individualScoreIntoInt > 0 && individualScoreIntoInt <= 21)
{
totalScore += individualScoreIntoInt;
scoreCount++;
}
//as mentioned in comment else here would also work, it's unnecessary to add any other validation.
else if (individualScoreIntoInt < 0 || individualScoreIntoInt > 21)
{
Console.WriteLine("Enter a score > 0 and < 21");
}
}
else
{
Console.WriteLine("Please only enter numbers");
}
}
}
}
}
I am currently working on a program that is a loop with a sentinel value that asks the user to enter a number or enter -99 to end the program and it runs perfectly. If I were to change that -99 to just the word "Quit" is there a certain parameter that I would have to put? For example, if I want to use a letter, I know that I could use:
char (undefined parameter) = 'A'
But how would I do this with a word? When I simply try to change the value of -99 to Quit, I receive an error as expected.
using System;
class Program {
public static void Main (string[] args) {
int sum = 0;
int counter = 0;
int max = Int32.MinValue;
int min = Int32.MaxValue;
bool keepGoing = true;
while(keepGoing) {
Console.WriteLine("Please enter a number or enter -99 to stop the program:");
int number = Convert.ToInt32(Console.ReadLine());
if (number == -99){
keepGoing = false;
} else {
counter++;
sum += number;
if (number >= max) {
max = number;
}
if (number <= min) {
min = number;
}
}
}
double average = (double) sum / counter;
Console.WriteLine($"{counter} numbers were entered.");
Console.WriteLine("The average is:" + average);
Console.WriteLine("The sum is:" + sum);
Console.WriteLine("The maximum value is:" + max);
Console.WriteLine("The minimum value is:" + min);
}
}
It's difficult to store "Quit" in an int, so the root of your problem is that you have no separation between pulling the string from the console and converting it to an int:
int number = Convert.ToInt32(Console.ReadLine());
if (number == -99){
keepGoing = false;
} else {
counter++;
If you did have a separation, it becomes possible:
string input = Console.ReadLine();
if (input == "Quit"){
keepGoing = false;
} else {
int number = Convert.ToInt32(input);
counter++;
A user enters two prime numbers which are then multiplied together, and another calculation of (a-1) * (b-1) is completed (a and b being the prime numbers entered). a function to checks the numbers entered, if the numbers are NOT prime, the user will be asked to re-enter the numbers. However, when I test this, I've noticed that if the user inputs a number which ISN'T prime, and then re-enters a prime number, the calculations are based on the number which ISN'T prime. E.g. if the user enters 2 and 4, since 4 isn't prime they are asked to enter another number, e.g 3, the calculations will be based on the numbers 2 and 4.
How can I correct this so it takes the valid prime number and not the invalid number originally entered?
namespace example
{
class Program
{
class Co_P
{
static void coprime(ref int c, int calculation)
{
if (gcd(c, calculation) == 1)
Console.WriteLine("it's Co-Prime");
else
do
{
Console.WriteLine("it isn't Co-Prime");
Console.WriteLine("Enter a Co-Prime");
c = int.Parse(Console.ReadLine());
coprime(ref c, calculation);
} while (gcd(c, calculation) != 1);
}
static int Prime_a(int a) //check a is prime
{
if (a <= 1) return 0;
for (int i = 2; i <= a / 2; i++)
{
if (a % i == 0)
{
return 0; //not prime
}
}
return 1;
}
static void result(int a) //outputs if a is prime/or not
{
if (Prime_a(a) != 0)
{
Console.WriteLine(a + " is a prime number");
}
else do
{
Console.WriteLine(a + " isn't prime number");
Console.WriteLine();
Console.WriteLine("Please make sure you enter a prime number");
a = int.Parse(Console.ReadLine());
} while (Prime_a(a) == 0);
}
static int Prime_b(int b)
{
if (b <= 1) return 0;
for (int i = 2; i <= b / 2; i++)
{
if (b % i == 0)
{
return 0;
}
}
return 1;
}
static void resultb(int b)
{
int result = Prime_b(b);
if (Prime_b(b) != 0)
{
Console.WriteLine(b + " is a prime number");
}
else do
{
Console.WriteLine(b + " is not a prime number");
Console.WriteLine("Please make sure you enter a prime number");
b = int.Parse(Console.ReadLine());
} while (Prime_b(b) == 0);
}
static void Main(string[] args)
{
int a;
Console.WriteLine("Enter a prime number for a");
a = int.Parse(Console.ReadLine());
Console.WriteLine();
result(a);
Console.WriteLine();
int b;
Console.WriteLine("Enter a prime number for b");
b = int.Parse(Console.ReadLine());
Console.WriteLine();
resultb(b);
Console.WriteLine();
int total = a * b;
Console.WriteLine("The total of the prime numbers is = " + total);
int calculation = (a - 1) * (b - 1); //calculation
Console.WriteLine();
Console.WriteLine("The result = " + calculation);
Console.WriteLine();
}
}
}
You should extend result and resultb function so it returns new prompted valid number
static int result(int a) {
var result = Prime_a(a);
if (result != 0)
...code...
return result
}
Also don't forget to reassign those values
...code...
a = result(a);
...code...
b = resultb(b);
int b;
Console.WriteLine("Enter a prime number for b");
b = int.Parse(Console.ReadLine());
Console.WriteLine();
resultb(b);
Console.WriteLine();
In line resultb(b); you are passing int to method resultb. int is a value type, or in other words, passing int to a method means passing its value to a method, where copy of that value is created. In this case a copy of b is created in method resultb. Every further change on b inside method resultb is made on copy and original stays the same.
In resultb method pass parameter by reference by adding ref keyword. Instead
static void resultb(int b)
{
// code
}
method will look like this
static void resultb(ref int b)
{
// code
}
You will call the method this way
resultb(ref b);
Here's the portion of code.
int b;
Console.WriteLine("Enter a prime number for b");
b = int.Parse(Console.ReadLine());
Console.WriteLine();
resultb(ref b);
Console.WriteLine();
Now every change on passed b inside method resultb will reflect on the original.
You should do the same for method result(int a).
When I enter the number 6 to calculate its factorial, it returns 30 (which is wrong).
Why is my program producing incorrect output?
using System;
namespace Scenario1_2
{
class Program
{
static void Main(string[] args)
{
int counter, number, fact;
Console.WriteLine("Please enter the number you wish to factorize");
number = int.Parse(Console.ReadLine());
fact = number;
for (counter = number - 1; counter >= 1; counter--)
{
fact = fact * counter;
Console.WriteLine("The number you entered was {0} and it's factorial is {1}", number, fact);
Console.ReadLine();
}
}
}
}
You look new to programming, or least C#, so just for fun, this will blow your mind:
using System;
namespace Scenario1_2
{
class Program
{
static void Main(string[] args)
{
Console.WriteLine("Please enter the number you wish to factorize");
int number = int.Parse(Console.ReadLine());
Console.WriteLine("The number you entered was {0} and it's factorial is {1}", number, Factorial(number));
Console.ReadKey(true);
}
static int Factorial(int n)
{
if (n >= 2) return n * Factorial(n - 1);
return 1;
}
}
}
No loops anywhere, and the function calls itself.
You can also do it like this:
using System;
namespace Scenario1_2
{
class Program
{
static void Main(string[] args)
{
Console.WriteLine("Please enter the number you wish to factorize");
int number = int.Parse(Console.ReadLine());
Console.WriteLine("The number you entered was {0} and it's factorial is {1}", number, Factorial(number));
Console.ReadKey(true);
}
static int Factorial(int n)
{
return Enumerable.Range(1, n).Aggregate((i, r) => r * i);
}
}
}
Which is all kinds of messed up :) ...but it does get the significant work down to a single line of code.
Then there's my personal favorite, the infinite enumerable:
using System;
namespace Scenario1_2
{
class Program
{
static void Main(string[] args)
{
Console.WriteLine("Please enter the number you wish to factorize");
int number = int.Parse(Console.ReadLine());
Console.WriteLine("The number you entered was {0} and it's factorial is {1}", number, Factorials().Skip(number-1).First());
Console.ReadKey(true);
}
static IEnumerable<int> Factorials()
{
int n = 1, f = 1;
while (true) yield return f = f * n++;
}
}
}
The program is paused waiting for some input. You need to move the second Console.ReadLine() out of the loop. And likely the Console.WriteLine() unless you want to see each iteration completing.
You need to move two lines out from the for loop. The modified code look like this.
using System;
namespace Scenario1_2
{
class Program
{
static void Main(string[] args)
{
int counter, number, fact;
Console.WriteLine("Please enter the number you wish to factorize");
number = int.Parse(Console.ReadLine());
fact = number;
for (counter = number - 1; counter >= 1; counter--)
{
fact = fact * counter;
}
Console.WriteLine("The number you entered was {0} and it's factorial is {1}", number, fact);
Console.ReadLine();
}
}
}
There are lots of ways to calculate Factorial. You can also do it by creating a recursive function. Google can help you a lot on these basic things.
Thanks!
int n = 4, fact = n;
for (int i = n; i > 1; i--)
{
fact *= (i - 1);
}
Console.WriteLine(fact);
Console.ReadLine();
why are You printing the message inside the loop.put it outside the loop
Console.WriteLine("The number you entered was {0} and it's factorial is {1}", number, fact);
using System;
namespace factorial
{
class Program
{
static void Main(string[] args)
{
int fact = 1;
Console.Write("Enter a number to find factorial:");
int n = int.Parse(Console.ReadLine());
for (int i = n; i > 0; i--)
{
fact = fact * i;
}
Console.Write("Factorial of" + n +"is :"+fact);
Console.ReadLine();
}
}
}
import java.util.Scanner;
public class Chapter5ProblemTwelve
{
public static void main(String [] args)
{
Scanner keyboard = new Scanner(System.in);
int number;
int factor = 1;
int counter;
System.out.print("Enter a positive integer to display the factorial number: ");
number = keyboard.nextInt();
//If the number entered is less then zero. The program will tell the user to enter a positive number
if (number <= 0)
{
System.out.println("Please enter a postive number and rerun the program again.");
}
else
{
// Math work preformed if user enters a postive number. Example if user enters 4.
// 1*1 = 1, 1*2 = 2,1*3 = 3, 1*4 = 4, The program will multiple all the answers together 1*2*3*4 = 24
for (counter = 1; counter <= number; counter++)
{
factor = factor * counter;
}
//display
System.out.println("The factorial number of " + number + " is: " + factor);
}
}
}
using System;
namespace septtwenty
{
class Program
{
static void Main(string[] args)
{
int i, number, fact;
System.Console.WriteLine("Enter the Number");
number = int.Parse(Console.ReadLine());
fact = number;
for (i = number -1; i>=1; i--)
{
fact = fact * i;
}
System.Console.WriteLine("\nFactorial of Given Number is: "+fact);
Console.ReadLine();
}
}
}
I am new to programming and I think I have confused myself I'm trying to make a loop that asks users for integers when the user inputs a integer greater than 100 then the console displays the amount of integers the user has input and the sum of these integers. I know it's basic but I can't figure where I went wrong.
namespace Wip
{
class Program
{
static void Main(string[] args)
{
string strNum1, strNum2;
int num1, num2;
int i = 0;
int sum =0 ;
Console.WriteLine("Please enter a integer between 1 and 100"); // asks for user input
strNum1 = Console.ReadLine();
num1 = int.Parse(strNum1);
do //repeat asking for user input
{
Console.WriteLine("Please enter another integer between 1 and 100"); // asks for user input
strNum2 = Console.ReadLine();
num2 = int.Parse(strNum2); //input is stored as num2
sum = num2; //store num2 in sum
i++;
if (num2 >= 100) // if num2 int is greater than 100
{
sum = (num1 +num2 +sum); // do calculation
Console.WriteLine("No of integers entered is {0} {1}", i, sum); //output calculation
}
}
while (i < 100);
}
}
}
any help would be appreciated thanks everyone!
You're on the right track... a couple of things:
Do... While is used when you always want to run through the block at least once, so your first 'get' from the user can be inside the block. You can code whatever you want to happen after the condition fails right after the block, instead of checking the same condition inside it.
Make sure if you're simply using Parse that you wrap it in a try...catch, because your user could type in anything (not just numbers). Personally I usually use TryParse instead.
Finally, make sure you're comparing to the correct variable. Checking that i < 100 will keep looping until 100 numbers have been entered; you want to compare the user's input instead.
namespace Wip
{
class Program
{
static void Main(string[] args)
{
string prompt = "Please enter {0} integer between 1 and 100";
string strNum;
int num = 0;
int i = 0;
int sum =0 ;
do //ask once and repeat while 'while' condition is true
{
string pluralPrompt = i > 0 ? "another" : "an";
prompt = string.Format(prompt,pluralPrompt);
Console.WriteLine(prompt); // asks for user input
strNum = Console.ReadLine();
if (!Int32.TryParse(strNum, out num)) //input is stored as num
{
// warn the user, throw an exception, etc.
}
sum += num; //add num to sum
i++;
}
while (num < 100);
Console.WriteLine("No of integers entered is {0} {1}", i, sum); //output calculation
}
}
}
namespace Wip
{
class Program
{
static void Main(string[] args)
{
string strNum;
int num;
int i = 0;
int sum = 0;
do //repeat asking for user input
{
Console.WriteLine("Please enter another integer between 1 and 100"); // asks for user input
strNum = Console.ReadLine();
if (int.TryParse(strNum, out num)) //input is stored as num2
{
if (num < 101)
{
i++;
sum += num;
continue;
}
else
{
Console.WriteLine("No of integers entered is {0} {1}", i, sum); //output calculation
break;
}
}
}
while (i < 100);
}
}