Hollow Square Inside Hollow Square C# - c#

Hello is it possible to create this kind of patter using console c#?
Input 1: 5
Input 2 :3
Expected Output:
*****
* * *
*** *
* *
*****
Here the top-left of the 5x5 box overlaps with the top-left of the 3x3 box.
I already tried to recreate this patter but i ended up with just whole square with cross inside
Example of my code below:
int num1,num2, i, j;
Console.WriteLine("Input 1");
num1 = Convert.ToInt32(Console.ReadLine());
Console.WriteLine("Input 2");
num2 = Convert.ToInt32(Console.ReadLine());
for(i = 0;i < num1;i++)
{
for(j = 0;j < num1;j++)
{
if(i == 0 || i == num1 - 1)
{
Console.Write(" * ");
}
else if(j == 0 || j == num1 - 1)
{
Console.Write(" * ");
}else if (j == num2 -1 || i == num2 -1){
Console.Write(" * ");
}
else
{
Console.Write(" "); // space is printed ..
}
}
Console.WriteLine("");
}
Console.ReadLine();
Input 1: 5
Input 2: 3
Output:
*****
* * *
*****
* * *
*****

The reason you're seeing the output you are is that you are also considering values beyond the edges of box 2 as being within the box (along edge lines).
That is to say that your intention is to draw the black lines and the blue lines, but you're continuing the vertical line down (red) and the horizontal line across (red). In these situations, you need to restrict the line vertically or horizontally to ensure you don't extend it too far.
I would create two flags for each of the boxes:
bool borderOfOuterBox =
i == 0 // top
|| j == 0 // left side
|| i == (num1 - 1) // bottom
|| j == (num1 - 1); // right side
bool borderOfInnerBox =
i == 0 // top
|| j == 0 // left side
|| (i == (num2 - 1) && j < num2) // bottom (note j is within the bounds of num2)
|| (j == (num2 - 1) && i < num2); // right side (not i is within the bounds of num2)
Then the whole check for writing becomes this:
bool borderOfOuterBox = i == 0 || j == 0 || i == (num1 - 1) || j == (num1 - 1);
bool borderOfInnerBox = i == 0 || j == 0 || (i == (num2 - 1) && j < num2) || (j == (num2 - 1) && i < num2);
if (borderOfOuterBox || borderOfInnerBox)
{
Console.Write(" * ");
}
else
{
Console.Write(" "); // space is printed ..
}

Related

How to stop a while loop? C#

I am very new to C# and while loops. Does anyone know how to stop it? It keeps printing the first if-statement. Here is the code:
const int Year = 400;
const int LeapYear = 4;
const int NoLeapYear = 100;
int input = 0;
input = int.Parse(Console.ReadLine());
while (input != 0)
{
Console.WriteLine("Enter a number: ");
if (input > 0 && input % LeapYear == 0 || input % Year == 0)
{
Console.WriteLine($"{input} is a leap year.");
}
if (input > 0 && input % NoLeapYear != 0)
{
Console.WriteLine($"{input} is not a leap year.");
}
if (input < 0)
{
Console.WriteLine("Year must be positive!");
}
if (input == 0)
{
Console.WriteLine("End of program");
}
}
You have to read the input inside the while loop:
const int Year = 400;
const int LeapYear = 4;
const int NoLeapYear = 100;
int input = -1; // initialize to something different than zero, to enter the while loop (or use do while loop instead of while loop)
while (input != 0)
{
Console.WriteLine("Enter a number: ");
input = int.Parse(Console.ReadLine()); // you were missing this line
if (input > 0 && input % LeapYear == 0 || input % Year == 0)
{
Console.WriteLine($"{input} is a leap year.");
}
if (input > 0 && input % NoLeapYear != 0)
{
Console.WriteLine($"{input} is not a leap year.");
}
if (input < 0)
{
Console.WriteLine("Year must be positive!");
}
if (input == 0)
{
Console.WriteLine("End of program");
}
}
Consider using a do while loop in this case.
If you are using loop just and break to true statement It will breaks it
while (input != 0) {
conditions;
break; // Breaks the loop
}
Use the break; keyword to stop any loop in C# not just C# in many languages also break is used to stop loops
Or,
Satisfy the condition to opposite of what you have it will break/stop the loop
use break (https://www.w3schools.com/cs/cs_break.php)
int i = 0;
while (i < 10)
{
Console.WriteLine(i);
i++;
if (i == 4)
{
break;
}
}

Correctly determining if an IList<int> already exists in IList<IList<int>>

I'm using 3 iterators to iterate through an int[] object to find lists containing three int's that all sum to 0, without adding duplicate lists to the final return object. Once the iterators find a valid sequence, each array value that the iterator points to is added to a temporary IList object via syntax such as "tempList.Add(nums[a]);" e.t.c. This tempList is then added to the final IList<IList> return object.
To check for duplicates, I'm using the following sytax:
if ((nums[c] + nums[a] + nums[b] == 0) && !answerList.Contains(tempList))
{
answerList.Add(tempList);
}
This works when the IList<IList> is initially empty, however the second clause evaluated "false" for the following scenario, which is preventing the valid tempList from being added to the IList<IList> answerList :
IList<IList<int>> == [[-1,0,1]]
tempList == [-1,-1,2]
Do I need to extend a Comparable interface to correct this? I've double checked the array values for a, b and c and they collectively sum to 0, so I'm certain that it's the .Contains comparison that is causing issue.
Here is the code:
public IList<IList<int>> ThreeSum(int[] nums) // maybe use three index pointers to fill triplet, one starting at index 0, one
// starting at index nums.Lenght - 1 and one starting near or at middle
// 5 billion possible combinations of triplets among array of 3001 triplets
{
IList<int> tempList = new List<int>();
IList<IList<int>> answerList = new List<IList<int>>();
int countPositive = 0;
int countNegative = 0;
bool addAnswerList = false;
int indexPositive = 0;
int a = 0;
int b = 0;
int c = 0;
bool aExtreme = false;
bool bExtreme = false;
bool cExtreme = false;
if (nums == null)
return answerList;
if (nums.Length == 0 /* || /* nums.Length < 3 */)
return answerList;
if (nums.Length == 1 && nums[0] == 0)
return answerList;
for (int i = 0; i < nums.Length; i++) // corner case where all array values are either postive or negative
// 0 sum triplet not possible
{
if (nums[i] > 0)
countPositive++;
else if (nums[i] < 0)
countNegative++;
}
if ((countPositive == nums.Length || countNegative == nums.Length) || (countNegative == 0 && countPositive == 0))
return answerList;
if (nums.Length < 51)
{
int temp = 0;
for (int i = 1; i < nums.Length; i++) // use recursive sort to go through 3001 elements, use linear if less than 51
{
temp = nums[i];
int j = i;
while (j > 0 && nums[j-1] > temp)
{
nums[j] = nums[j-1];
j--;
}
nums[j] = temp;
}
Console.WriteLine(String.Join(" ", nums));
}
else if (nums.Length > 50) // recursive sort for larger input array
{
mergeSort(nums);
}
// Now nums is storted, 0 sum triplet will most likely be found where entries change from negative to positive
for (int i = 0; i < nums.Length; i++)
{
if (nums[i] > 0)
{
// toPositive = true;
indexPositive = i;
break;
}
}
Console.WriteLine(indexPositive);
if (indexPositive == 0) // case to make sure accessors do not get invalid number
{
a = 0; // initialize other two index accessors in addition to indexPositive
b = 0;
}
else
{
a = indexPositive - 1; // initialize other two index accessors in addition to indexPositive
b = indexPositive - 1;
}
c = indexPositive; // store initial indexPositive value into variable c as indexPositive will change
// throughtout the interation
// if indexPositive is less than (nums.Length / 2), iterate two other accessors towards end of nums
// else, interate two other accessors towards nums[0]
if (c < (nums.Length / 2)) // use iterator c in place of indexPositive
{
while (c < nums.Length && b < nums.Length && a >= 0)
{
if (a == 0 || a == nums.Length - 3)
{
aExtreme = true;
}
else
{
aExtreme = false;
}
if (b == 1 || b == nums.Length - 2)
{
bExtreme = true;
}
else
{
bExtreme = false;
}
if (c == 2 || c == nums.Length - 1)
{
cExtreme = true;
}
else
{
cExtreme = false;
}
if ((c != a && c != b && a != b) && (nums[c] + nums[a] + nums[b] == 0)) // if nums add to 0, add them to tempList
{
tempList.Add(nums[a]);
tempList.Add(nums[b]);
tempList.Add(nums[c]);
}
// need to check if exact triplet is duplicate or if tempList triplet contains same 3 values in different order
// 3 values in different order not an issues since input list is already sorted!!!!
// but need to be aware order accessors are added to temp list. Accessors cannot "crossover" one another!!!
if ((nums[c] + nums[a] + nums[b] == 0) && !answerList.Any(x => x.SequenceEqual(tempList)) /*!answerList.Contains(tempList)*/)
// Having issues, answerList.Contains does not currently do what is desired
{
answerList.Add(tempList); // add tempList to answerList
addAnswerList = true;
}
else
{
addAnswerList = false;
}
tempList.Clear(); // clear tempList to prepare for next entry
// Make changes here to make sure only 1 accessor iterates at a time, to check all possible and logical combinations
// Since array is now sorted, iteration towards sums[0] only has to continue if sum of 3 accessors is greater than 0
// Once active accessor returns a value that results in 0 sum, further iteration is guaranteed to return
// an identical triplet or one that sums to less than 0. At this point, the two accessors that are going in the same
// direction should be iterated by 1 position and the cycle repeated
if (nums[a] + nums[b] + nums[c] < 0) // still have chance to get to 0 value triplet with rightmost accessor
{
c++;
}
else if ((addAnswerList == true) || nums[a] + nums[b] + nums[c] > 0) // no point in further iteration,
// reset 'c' accessor to original starting
// position and decrement other accessors by 1
// towards first array element
{ // to begin cycle again
c = indexPositive - 1;
b--;
a--;
}
}
}
else // a and b accessors are interated towards 0
{
while (c < nums.Length && a >= 0 && b >= 0)
{
if (a == 0 || a == nums.Length - 3)
{
aExtreme = true;
}
else
{
aExtreme = false;
}
if (b == 1 || b == nums.Length - 2)
{
bExtreme = true;
}
else
{
bExtreme = false;
}
if (c == 2 || c == nums.Length - 1)
{
cExtreme = true;
}
else
{
cExtreme = false;
}
if ((c != a && c != b && a != b) && (nums[c] + nums[a] + nums[b] == 0)) // if nums add to 0, add them to tempList
// need to check if exact triplet is duplicate
{
tempList.Add(nums[a]);
tempList.Add(nums[b]);
tempList.Add(nums[c]);
}
Console.WriteLine(String.Join(" ", tempList));
// need to check if exact triplet is duplicate or if tempList triplet contains same 3 values in different order
// 3 values in different order not an issues since input list is already sorted!!!!
// but need to be aware order accessors are added to temp list. Accessors cannot "crossover" one another!!!
if ((nums[c] + nums[a] + nums[b] == 0) && !answerList.Any(x => x.SequenceEqual(tempList)))
// Having issues, answerList.Contains does not currently do what is desired
{
answerList.Add(tempList); // add tempList to answerList
addAnswerList=true;
}
else
{
addAnswerList = false;
}
tempList.Clear(); // clear tempList to prepare for next entry
// Make changes here to make sure only 1 accessor iterates at a time, to check all possible and logical combinations
// Since array is now sorted, iteration towards sums[0] only has to continue if sum of 3 accessors is greater than 0
// Once active accessor returns a value that results in 0 sum, further iteration is guaranteed to return
// an identical triplet or one that sums to less than 0. At this point, the two accessors that are going in the same
// direction should be iterated by 1 position and the cycle repeated
if (nums[a] + nums[b] + nums[c] > 0) // still have chance to get to 0 value triplet with
// leftmost accessor
{
a--;
}
else if ((addAnswerList == true) || nums[a] + nums[b] + nums[c] < 0) // no point in further iteration,
// reset 'a' accessor to original starting
// position and increment other accessors by 1
// towards last array element
{ // to begin cycle again
a = b; // a = indexPositive - 1;
if ((bExtreme == false && b < nums.Length - 2) && (cExtreme == false && c < nums.Length - 1))
// if there is still room to run towards end of array, increment, else decrement
{
b++;
c++;
}
else
{
bExtreme = true;
cExtreme = true;
a -= 2;
b--;
}
}
}
}
Console.WriteLine(String.Join(" ", answerList));
return answerList;
}
public void merge(int[] array1, int[] array2, int[] outArray)
{
int i = 0;
int j = 0;
while (i + j < outArray.Length)
{
if (j == array2.Length || (i < array1.Length && (array1[i] < array2[j])))
{
outArray[i + j] = array1[i++];
}
else
{
outArray[i + j] = array2[j++];
}
}
}
public void mergeSort(int[] inputArray)
{
if (inputArray.Length < 2)
return;
int[] firstHalf = new int[inputArray.Length / 2];
int[] secondHalf = new int[inputArray.Length / 2];
for (int i = 0; i < (inputArray.Length / 2); i++)
{
firstHalf[i] = inputArray[i];
}
for (int i = inputArray.Length / 2; i < inputArray.Length; i++)
{
secondHalf[i] = inputArray[i];
}
mergeSort(firstHalf);
mergeSort(secondHalf);
merge(firstHalf, secondHalf, inputArray);
}
You can replace
answerList.Contains(tempList))
which checks only for reference equality, with
answerList.Any(x => x.SequenceEqual(tempList))
which will run SequenceEqual on the answerList until it finds the first answer that has the same integer elements and returns false if none can be found.
Keep in mind that these functions require System.Linq.
Credit: thanks Hans Kesting for suggesting Any(...) over FirstOrDefault(...) != null

Replace if number statements with text

I am trying to complete this assignment where if an integer is divisible by 2,3, and 7, it replaces the following numbers (25-50) with "BuzzLightYear"
I have the numbers listed correctly, but when I run the program it prints the text along with the number when I just want the text instead of the number.
Here is my code:
int variable = 25;
while (variable <= 50)
{
Console.WriteLine(variable + "\n");
++variable;
if (variable % 2 == 0 && variable % 3 == 0 && variable % 7 == 0)
{
Console.Write("BuzzLightYear");
}
}
Console.ReadKey();
int variable = 25;
while (variable <= 50)
{
if (variable % 2 == 0 && variable % 3 == 0 && variable % 7 == 0)
{
Console.Write("BuzzLightYear\n\n");
}
else
{
Console.WriteLine(variable + "\n");
}
++variable;
}
Console.ReadKey();
int variable = 25;
while (variable <= 50)
{
if (variable % 2 == 0 && variable % 3 == 0 && variable % 7 == 0)
{
Console.Write("BuzzLightYear");
}
else{
Console.WriteLine(variable + "\n");
}
++variable;
}
Console.ReadKey();
The problem is that you're always printing the number. Just put that in an else instead.
But anytime you need a set number of iterations, a for loop is generally better because the loop variable declaration, condition, and increment are all in one place:
for (int variable = 25; variable <= 50; variable++)
{
if (variable % 2 == 0 && variable % 3 == 0 && variable % 7 == 0)
{
Console.WriteLine("BuzzLightYear");
}
else
{
Console.WriteLine(variable);
}
}
Console.ReadKey();

Ideal behavior for a constraint in online test c#

I want to know how to proceed if a console input is not met in a online test.
Like - 0 > x > 10
Sample question -
Please take two inputs from user and return the sum of the both.
Constraint -
0 < a < 10
2 < b <= 15
Below are solutions I have tried with their success rate.
Case 1:
int a = Convert.ToInt32(Console.ReadLine());
while (a < 1 || a > 9)
a = Convert.ToInt32(Console.ReadLine());
int b = Convert.ToInt32(Console.ReadLine());
while (b < 3 || b > 15)
b = Convert.ToInt32(Console.ReadLine());
Success - 35 %
Case 2
int a = Convert.ToInt32(Console.ReadLine());
if(a < 1 || a > 9)
Environment.Exit(0);
int b = Convert.ToInt32(Console.ReadLine());
if(b < 3 || b > 15)
Environment.Exit(0);
Success - 35 %
Case 3:
try
{
int a = Convert.ToInt32(Console.ReadLine());
if (a < 1 || a > 9)
throw new ArgumentException();
int b = Convert.ToInt32(Console.ReadLine());
if (b < 3 || b > 15)
throw new ArgumentException();
return a + b;
}
catch(ArgumentException ex)
{
Console.WriteLine(ex);
}
Success - 0%
Case 4: Without Constraint
int a = Convert.ToInt32(Console.ReadLine());
int b = Convert.ToInt32(Console.ReadLine());
return a + b;
Success - 95%
So what am I missing to get 100%
You would need to do a validation of some sort. Don't use an "Environment.Exit" because a while loop doesn't work like that. A while loop will continue until it returns "False" for example see the code below to validate digit input in the console.
while(!int.TryParse(someString, out int someInt))
{
Console.WriteLine("Your variable someString contains something other than numbers.");
}
Your code might look something like this.0 > x > 10
while(x < 0 || x > 10)
{
Console.WriteLine("Do this code.");
}
Constraints:
0 < a < 10
2 < b <= 15
Code:
int a;
int b; //Declare these outside the loop.
while(!(a > 0 && a < 10 && b > 2 && b <=15))
{
Console.WriteLine("Please Input a valid number for A.");
a = Console.ReadLine();
Console.WriteLine("Please Input a valid number for B.";
b = Console.ReadLine();
}
int sum = a + b;
Console.WriteLine($"The sum is {sum}.");

Non square spiral matrix not printing correctly

I am having issues with this assignment I have. I am to print a spiral matrix which cannot be square, in other words the user should input the number of rows and columns.
Console.Write("Enter n: ");
int n = int.Parse(Console.ReadLine());
Console.Write("Enter m: ");
int m = int.Parse(Console.ReadLine());
int[,] matrix = new int[n,m];
int row = 0;
int col = 0;
string direction = "right";
int maxRotations = n * m;
for (int i = 1; i <= maxRotations; i++)
{
if (direction == "right" && (col > n - 1 || matrix[row, col] != 0))
{
direction = "down";
col--;
row++;
}
if (direction == "down" && (row > n - 1 || matrix[row, col] != 0))
{
direction = "left";
row--;
col--;
}
if (direction == "left" && (col < 0 || matrix[row, col] != 0))
{
direction = "up";
col++;
row--;
}
if (direction == "up" && row < 0 || matrix[row, col] != 0)
{
direction = "right";
row++;
col++;
}
matrix[row, col] = i;
if (direction == "right")
{
col++;
}
if (direction == "down")
{
row++;
}
if (direction == "left")
{
col--;
}
if (direction == "up")
{
row--;
}
}
// displej matrica
for (int r = 0; r < n; r++)
{
for (int c = 0; c < m ; c++)
{
Console.Write("{0,4}", matrix[r,c]);
}
Console.WriteLine();
}
Console.ReadLine();
}
My issue currently is that is not printing and at the same is printing in a spiral. In other words the spiral is kind of messed up.
If i run the code and enter 4 as the number of rows and 6 as the number of columns I get the following:
1 2 3 4 0 24
12 13 14 5 0 23
11 16 17 18 19 22
10 9 8 7 20 21
What am i doing wrong?
Your first two conditions check the same boundary (n):
if (direction == "right" && (col > n - 1 || matrix[row, col] != 0))
if (direction == "down" && (row > n - 1 || matrix[row, col] != 0))
I guess for "right" your boundary should be m.
if (direction == "right" && (col > m - 1 || matrix[row, col] != 0))
That's why it is "turning" early: n is 4. And that's exactly where it is turning. The rest are all follow-up errors.

Categories