Updating a sum (Ex. spaces = spaces + 2) with for loop - java

Okay, I'm making a program that'll make vertical lines, horizontal lines, diagonals lines too! I'm kinda confused on one of my outputs that doesn't make any sense.
So my psudocode was like this:
//enter a char
//enter a number that will determine how long the line is
//define with easyreader what type of line it will be (hori, vert, diag)
//the idea of making the diag lines was this...
#
(two spaces) #
(four spaces) #
(six spaces) #
//we could use the sum spaces = spaces + 2; to keep on calculating what
//the previous spaces was
Code was:
class starter {
public static void main(String args[])
{
System.out.print("What char would you like? ");
EasyReader sym = new EasyReader();
String chars = sym.readWord();
System.out.print("How long would you like it to be? ");
int nums = sym.readInt();
System.out.print("Diag, Vert, or Hori? ");
//you want to read the __ varible, not the sym.readX()
String line = sym.readWord();
System.out.println("");
System.out.println("");
if(line.equals("Hori")){
for(int x = 0; x < nums; x++){
System.out.print(chars + " ");
}
}
else if(line.equals("Vert")){
for(int y = 0; y < nums; y++){
System.out.println(chars + " ");
}
}
else{
for(int xy = 0; xy < nums; xy++){
for(int spaces = 0; spaces < nums; spaces++){
spaces = spaces + 2;
System.out.print(spaces + " ");
System.out.println(chars);
}
}
}
}
}
At the bottom you will see a for loop called xy that will read how long the lines would be. Under that for loop would control the spaces. However, for some reason, the sum isn't updating correctly. The output is always:
2 (char)
5 (char)
8 (char)
2 (char)
5 (char)
8 (char)
...
The output should be:
2 (char)
4 (char)
8 (char)
...
EDIT **********
Since I need help now changing incriements here is an example (So I don't have to explain it a lot in comments)
Example: If user puts he wants the line as much as 5 units. With two for loops, one controlling how many spaces he wants, one controlling how many chars will print out, the output would be then 2, 4, 6, 8, 10.

In for loop statement, you say 'increase spaces by one after each iteration' (spaces++):
for(int spaces = 0; spaces < nums; spaces++){
In the body of your loop, you additionally ask to increase it by 2:
spaces = spaces + 2;
So each iteration it gets increased by 3.
By the way, there seems to be something wrong with your nested loops (if I understand the intention correctly). If the outer loop (looping over xy) draws a line on each iteration, then the inner loop, which is supposed to output an indent for the current line, must be bounded by xy (multiplied by 2) rather than nums. I'd write it like this:
for (int xy = 0; xy < nums; xy++) {
for (int spaces = 0; spaces < xy*2; spaces += 2) {
System.out.print(" ");
}
System.out.println(chars);
}

Because you are adding 3 to the spaces each time
for(int spaces = 0; spaces < nums; spaces++){
spaces = spaces + 2;
spaces++ spaces += 1
spaces = spaces + 2; spaces += 2

actually the problem is in this part :
for(int spaces = 0; spaces < nums; spaces++){
spaces = spaces + 2;
System.out.print(spaces + " ");
System.out.println(chars);
}
when the program starts we have spaces = 0
then this part is going to run spaces =spaces + 2
now spaces is equal to 2, so we have spaces = 2
the program prints 2, after that spaces increments by 1 using spaces++ part
now spaces is equal to 3, which means spaces=3
after that this line is going to be run spaces = spaces + 2
so the value of spaces becomes 5
and if we do this for ever and ever we will have this sequence of numbers :
2 5 8 11 14 ....
in fact this is because we are incrementing spaces by 3 in each iteration
if you modify your code in this form, the problem is going to be solved :
for (int xy = 0; xy < nums; xy++) {
for(int spaces = 0; spaces < xy*2; spaces += 2)
System.out.print(spaces + " ");
System.out.println(chars);
}

Related

Displaying a pyramid

I have this task to display a pyramid as follows:
I wrote the code but unfortunately, the digits are displayed with spaces and order.
public class DisplayPyramid {
//main method declaration. Program entry point which begins its execution
public static void main(String[] args) {
//Create a Scanner object
Scanner input = new Scanner(System.in);
//Prompt the user to enter an integer (number of lines)
System.out.print("Enter the number of lines: ");
int numbers = input.nextInt(); //Read value from keyboard and assign it to numberOfLines
String padding = " ";
//Display pyramid
//for loop to produce each row
for (int rows = 0; rows < numbers ; rows++) {
for (int k = numbers - rows; k >= 1; k--){
System.out.print(k + " ");
}
for (int l = 2; l <= numbers - rows; l++){
System.out.print(" " + l);
}
//Advance to the next line at the end of each rows
System.out.print("\n");
}
} }
And this is my output:
Can you help me figure out what is wrong with code ?
Anyone's help will be much appreciated.
Consider the 1st pass of the outer loop which produces
If we color hint your code, which the first inner loop in red, the second inner loop in green
This will be their corresponding output for each pass
The last pass of the red loop print "1 " and the first pass of green loop print " 2". They combine and become "1 2", which has 2 spaces in between.
The solution as Osama A.R point out, just reverse the printing order of number and space for the green loop and make if follow the red loop pattern. That will make the sequence neat.
Your second for loop prints the spaces first and then the number, however, the spaces have already been added by the first for loop, so just update the second for loop to print the spaces after printing the number.
E.g. your second loop should be like this:
for (int l = 2; l <= numbers - rows; l++){
System.out.print(l + " ");
}

How to construct a pyramid in Java

How do I construct a pyramid using a loop program, given a number of rows by a user's input? Such as
*
***
*****
*******
I've tried watching several videos and reading articles about the logic of this, but instructors were either not understandable or they skipped lines of reasoning.
I know every row increases by 2 stars, and I know that because every row has an odd number of stars I can define the number of stars in a row as 2n+1 where n is an integer. I noticed a 2 row triangle has a base of 3 stars, a 3 row triangle has a base of 5 stars, and so on. So for an nth row, the triangles base is n+(n-1), which is 2n-1. For example, r_5: base = 9 stars. The next thing I know my program needs to consider is spacing. I noticed, from the base, spacing increases by 2 every row until we have n-1 spaces on the first half and another n-1 spaces on the second half, in other words, spacing increases from the base until it is greater than or equal to 2b-2.
I think all that covers the gist a java program would need to know: the number of stars per row, the size of the base, and spacing.
But how do I translate all this in terms of a for while loop?
Method 1
Note that, if we denote current line number as "line" starting from 0, and total number of lines as "n",
Number of stars in each line = 2*line + 1
Number of leading (or trailing) spaces in each line = n - line - 1
We can simply generate the pyramid using this rule:
int n = 4;
for (int line = 0; line < n; line++) {
StringBuilder sb = new StringBuilder();
int starsToAppend = 2 * line + 1;
int spaceToAppend = n - line - 1;
while (spaceToAppend-- > 0) sb.append(" ");
while (starsToAppend-- > 0) sb.append("*");
System.out.println(sb.toString());
}
Method 2
You can also approach from the middle and expand. Note that there is a constant column of a star (*) in the middle, and on each side, only one star gets added in each line each time. And the rest are spaces.
int n = 4;
for(int line=0; line <n ; line++){
StringBuilder sb = new StringBuilder("*");
int spacesToAppendOnBothSides = n-line-1;
int starsToAppendOnBothSides = line;
for(int idx=0; idx<starsToAppendOnBothSides; idx++){
sb.insert(0, "*"); //appends to the beginning
sb.append("*"); //appends to the end
}
for(int idx=0; idx<spacesToAppendOnBothSides; idx++){
sb.insert(0, " ");
sb.append(" "); //NOTE: You may exclude this line to avoid adding trailing spaces
}
System.out.println(sb.toString());
}
Explanation:
On first iteration (line == 0) we take a single star,
*
and add zero extra stars (as our line# is zero) on both sides, which gives us (same string):
*
And then add n-line-1 (we substract 1 because we already added 1 character - the first star) = 3 spaces on each side of that star, which gives us:
...*...
On 2nd iteration (line == 1) if we apply same logic:
1.
*
***
^ This middle one is the first star
..***..
Pretty simple once you understand the logic.
There are multiple ways to do this, but these are among the simplest ones :)
Say you need to print a pyramid of n rows. You can see that row i (where i is between 1 and n) will start with n-i spaces and have (i-1)*2+1 asterisks:
for (int i = 1; i <= n; ++i) {
int spaces = n-i;
int stars = (i-1)*2+1;
for (int j = 1; j <= spaces; ++j) {
System.out.print(' ');
}
for (int j = 1; j <= stars; ++j) {
System.out.print('*');
}
System.out.println();
}
Here's my implementation -
public static String repeat(String str, int times) {
return new String(new char[times]).replace("\0", str);
}
public void createPyramid(int size) {
for (int i = 1; i <= size; i += 2) {
int numSpaces = (size - i) / 2;
System.out.println(repeat(" ", numSpaces) + repeat("*", i) + repeat(" ", numSpaces));
}
}
Call the method as - createPyramid(7); should give you the desired output. You can increase the size for bigger pyramid.
The variable i iterate for the size of the pyramid. And the number of stars on each row is increasing by 2 starting from 0. There i is incrementing by 2. The blank spaces will be equal to size - number of *'s but they have to be repeated before and after the *'s symmetrically, we divide it by 2. This will give the number of spaces before and after the *'s and in the middle we just need to print the *'s whose number is given by i.
So, we finally print them.
The repeat function creates a String formed from the str parameter repeated times times. eg - if we call repeat("abc", 3), it will return "abcabcabc".

Word Frequency Chart Problems

The goal of this code was to create a program using main method java to analysis a piece text which has been entered from a user.
They do this by entering the text into a scanner which is then analysed by the program. The analysis is to produce word frequency, mean length and also print out the results in a form of a asterisks chart, were a single "*" represents 1 words.
For example " Birds can maybe fly" produces this results:
Enter text:
Birds can maybe fly
Birds can maybe fly
1 letter words: 0
2 letter words: 0
3 letter words: 2
4 letter words: 0
5 letter words: 2
mean lenght: 4.0
1 letter words
2 letter words
3 letter words **
4 letter words
5 letter words **
So far I've completed the word frequency and the word mean, but the part I'm stuck on is creating the asterisks chart. This is an area in which I've never touch upon and was wondering how I would go about it, would I use a histogram or just use my int and then print out a "*" instead of a number?. I'm not expecting anyone to just hand me code, but if someone could give me a hint in what I should do or just point me the right direction or maybe just give me an explanation in what I should do, it would be greatly appreciated.
Code:
import java.util.Scanner;
public class Freq
{
public static void main(String[] args)
{
Scanner scan = new Scanner(System.in);
while (true)
{
System.out.println("Enter text: ");
String s;
s = scan.nextLine();
String input = s;
String strippedInput = input.replaceAll("\\W", " ");
System.out.println("" + strippedInput);
String[] strings = strippedInput.split(" ");
int[] counts = new int[6];
int total = 0;
for (String str : strings)
if (str.length() < counts.length)
counts[str.length()] += 1;
for (String s1 : strings)
total += s1.length();
for (int i = 1; i < counts.length; i++)
System.out.println(i + " letter words: " + counts[i]);
System.out.println(("mean lenght: ") + ((double) total / strings.length));
}
}
}
Commons Lang StringUtils.repeat()
Usage:
String str = "*";
int n = 2;
String repeated = StringUtils.repeat(str, n);
repeated will be: **
You could just loop over counts and for each cell print a number of asterisks equal to the number stored in it:
for (int i = 0; i < counts.length; ++i) {
StringBuilder sb = new StringBuilder(i).append(" letter words ");
for (int j = 0; j <= counts[i]; ++j) {
sb.append('*');
}
System.out.println(sb);
}

how to print a number triangle in java

I need to produce a triangle as shown:
1
22
333
4444
55555
and my code is:
int i, j;
for(i = 1; i <= 5; i++)
{
for(j = 1; j <= i; j++)  
{          
System.out.print(i); 
}      
System.out.print("\n");        
}
Producing a triangle the opposite way
1
22
333
4444
55555
What do i need to do to my code to make it face the right way?
You need 3 for loops:
Upper-level loop for the actual number to be repeated and printed
first inner level for printing the spaces
second inner level for to print the number repeatedly
at the end of the Upper-level loop print new line
Code:
public void printReversedTriangle(int num)
{
for(int i=0; i<=num; i++)
{
for(int j=num-i; j>0; j--)
{
System.out.print(" ");
}
for(int z=0; z<i; z++)
{
System.out.print(i);
}
System.out.println();
}
}
Output:
1
22
333
4444
55555
666666
I came across this problem in my AP CS class. I think you may be starting to learn how to program so heres what I'd do without giving you the answer.
Use a loop which removes the number of spaces each iteration. The first time through you would want to print four spaces then print 1 one time(probably done in a separate loop).
Next time through one less space, but print i one more time.
You need to print some spaces. There is a relation between the number of spaces you need and the number (i) you're printing. You can print X number of spaces using :
for (int k = 0; k < numSpaces; k++)
{
System.out.print(" ");
}
So in your code:
int i, j;
for(i = 1; i <= 5; i++)
{
// Determine number of spaces needed
// print spaces
for(j = 1; j <= i; j++)
{
System.out.print(i);
}
System.out.print("\n");
}
use this code ,
int i, j,z;
boolean repeat = false;
for (i = 1; i <= 5; i++) {
repeat = true;
for (j = 1; j <= i; j++) {
if(repeat){
z = i;
repeat = false;
while(z<5){
System.out.print(" ");
z++;
}
}
System.out.print(i);
}
{
System.out.print("\n");
}
}
You can use this:
int i, j;
int size = 5;
for (i = 1; i <= size; i++) {
if (i < size) System.out.printf("%"+(size-i)+"s", " ");
for (j = 1; j <= i; j++) {
System.out.print(i);
}
System.out.print("\n");
}
This line:
if (i < size) System.out.printf("%"+(size-i)+"s", " ");
Is going to print the left spaces.
It uses the old printf with a fixed sized string like 5 characters: %5s
Try it here: http://ideone.com/jAQk67
i'm having trouble sometimes as well when it's about formatting on console...
...i usually extract that problem into a separate method...
all about how to create the numbers and spacing has been posted already, so this might be overkill ^^
/**
* creates a String of the inputted number with leading spaces
* #param number the number to be formatted
* #param length the length of the returned string
* #return a String of the number with the size length
*/
static String formatNumber(int number, int length){
String numberFormatted = ""+number; //start with the number
do{
numberFormatted = " "+numberFormatted; //add spaces in front of
}while(numberFormatted.length()<length); //until it reaches desired length
return formattedNumber;
}
that example can be easily modified to be used even for Strings or whatever ^^
Use three loops and it will produce your required output:
for (int i=1;i<6 ;i++ )
{
for(int j=5;j>i;j--)
{
System.out.print(" ");
}
for(int k=0;k<i;k++)
{
System.out.print(i);
}
System.out.print("\n");
}
Your code does not produce the opposite, because the opposite would mean that you have spaces but on the right side. The right side of your output is simply empty, making you think you have the opposite. You need to include spaces in order to form the shape you want.
Try this:
public class Test{
public static void main (String [] args){
for(int line = 1; line <= 5; line++){
//i decreases with every loop since number of spaces
//is decreasing
for(int i =-1*line +5; i>=1; i--){
System.out.print(" ");
}
//j increases with every loop since number of numbers
//is decreasing
for(int j = 1; j <= line; j++){
System.out.print(line);
}
//End of loop, start a new line
System.out.println();
}
}
}
You approached the problem correctly, by starting with the number of lines. Next you have to make a relation between the number of lines (the first for loop) and the for loops inside. When you want to do that remember this formula:
Rate of change*line + X = number of elements on line
You calculate rate of change by seeing how the number of elements change after each line. For example on the first line you have 4 spaces, on the second line you have 3 spaces. You do 3 - 4 = -1, in other words with each line you move to, the number of spaces is decreasing by 1. Now pick a line, let's say second line. By using the formula you will have
-1(rate of change) * 2(line) + X = 3(how many spaces you have on the line you picked).
You get X = 5, and there you go you have your formula which you can use in your code as you can see on line 4 in the for loop.
for(int i = -1 * line +5; i >= 1; i--)
You do the same for the amount of numbers on each line, but since rate of change is 1 i.e with every line the amount of numbers is increasing by 1, X will be 0 since the number of elements is equal to the line number.
for(int j = 1; j <= line; j++){

Reading a file line and storing variables of different types

I am trying to figure out a way to read from the following text file. I am able to get the first integer in the text file which is numLines. After that point, I am able to get the first integer from the line, but am unable to successfully get each individual group of letters.
for(int i=0; i < numLines; i++){
numVariables = Integer.parseInt(fin.next());
for(int z=0; z < numVariables; z++){
String line = fin.next();
int numRules = Integer.parseInt(line.substring(0, 1));
//Everything up until this point is good
//read and store first capital letter of every line
String variable = line.substring(2,3);
//read and store remaining capital letters that correspond to every line separately
}
}
Text File
3
2 A CC DD
3 A AA z v
2 F f a
I didn't see what is the problem. If you say you have problem of "parsing", you could try:
read a line (String line)
split it into two parts. check here:
http://docs.oracle.com/javase/6/docs/api/java/lang/String.html#split(java.lang.String, int)
array =line.split(" ", 2)
then
array[0] is the leading number
array[1] is the rest letters
if you want each part, you could split (" ") without limit.
if you just want to get those Uppercase words, you can do it by regex:
line.split(" ",2); //array[0] is the leading number
apply "(?<= )[A-Z]+(?= )" on array[1], you get all Upper case words.
is that what you want?
String[] words = line.split(("\\s+"); // Any whitespace
int numRules = Integer.parseInt(words[0]);
for (int j = 1; j < words.length; ++j) {
String variable = words[j];
}

Categories

Resources