square of character inside square of another character in java - java

i want to print a square of character in this format basad on the the number of lines
for example :
number of lines : 4
output :
a a a a
a b b a
a b b a
a a a a
number of lines : 5
output :
a a a a a
a b b b a
a b c b a
a b b b a
a a a a a
but i didn't know how to get the result like that and this is my code
import java.util.Scanner;
public class test {
public static void main ( String arugs [] ) {
Scanner read= new Scanner(System.in) ;
System.out.println ( " please inter the number of line : " ) ;
int size = read.nextInt();
int []array = new int[size ];
int c = 97;
for(int i = 0; i < size; ++i) {
for(int j = 0; j < size; ++j){
array[i]= c;
System.out.print( (char)array [i]);}
System.out.println();
}
}
}
}

A funny way to do it :
public static void main(String arugs[]) {
Scanner sc = new Scanner(System.in);
System.out.println("Please enter the number of lines : ");
int size = sc.nextInt();
sc.close();
for (int i = 0; i < size; i++) {
for (int j = 0; j < size; j++) {
System.out.print((char) ('a' + Math.min(size - j - 1, Math.min(size - i - 1, Math.min(i, j)))) + " ");
}
System.out.println();
}
}
The idea :
we need to calculate the "depth" of a particular point (i, j). The value of this cell will be 'a' + depth
the depth is defined as the minimum distance of the point to any edge of the matrix

In method positionToChar, before the halfway point, the letters increase from a to max char point. At half way and afterwards, the letters decrease from max char point back to a.
There are basically two cases we are covering, even and odd.
For even:
Take the number 4 as input. Bear in mind that we are zero based.
positionToChar(0) -> 'a' + (0 < 4 / 2 ? 0 : 4 - 0 - 1) -> 0 is less than 4 / 2 or 2 so -> 'a' + 0 -> 'a' is returned.
positionToChar(1) -> 'a' + (1 < 4 / 2 ? 1 : 4 - 1 - 1) -> 1 is less than 4 / 2 or 2 so -> 'a' + 1 -> 'b' is returned.
positionToChar(2) -> 'a' + (2 < 4 / 2 ? 2 : 4 - 2 - 1) -> 2 is equal to 4 / 2 or 2 so -> 'a' + 4 - 2 - 1 -> 'b' is returned.
positionToChar(3) -> 'a' + (3 < 4 / 2 ? 3 : 4 - 3 - 1) -> 3 is greater than 4 / 2 or 2 so -> 'a' + 4 - 3 - 1 -> 'a' is returned.
For odd:
Take the number 3 as input. Bear in mind that we are zero based.
positionToChar(0) -> 'a' + (0 < 3 / 2 ? 0 : 3 - 0 - 1) -> 0 is less than 3 / 2 or 1 (truncated because we are using two ints) so -> 'a' + 0 -> 'a' is returned.
positionToChar(1) -> 'a' + (1 < 3 / 2 ? 1 : 3 - 1 - 1) -> 1 is equal to 3 / 2 or 1 (truncated because we are using two ints) so -> 'a' + 3 - 1 - 1 -> 'b' is returned.
positionToChar(2) -> 'a' + (2 < 3 / 2 ? 2 : 3 - 2 - 1) -> 2 is greater than 3 / 2 or 1 (truncated because we are using two ints) so -> 'a' + 3 - 2 - 1 -> 'a' is returned.
In method minChar, for a given position, the lower char of the computed chars for x and y is returned.
Take (x, y) pairs in 3 size:
First layer:
(0, 0) -> In the previous example, we calculated 0 to be 'a'.'a' is returned as is the only char we have.
(0, 1) -> In the previous example, we calculated 0 to be 'a' and 1 to be 'b'. 'a' is returned as it is the smaller of the two.
(0, 2) -> In the previous example, we calculated both 0 and 2 to be 'a'. 'a' is returned as is the only char we have.
Second layer:
(1, 0) -> In the previous example, we calculated 1 to be 'b'and 0 to be 'a'. 'a' is returned as it is the smaller of the two.
(1, 1) -> In the previous example, we calculated 1 to be 'b'. 'b' is returned as is the only char we have.
(1, 2) -> In the previous example, we calculated 1 to be 'b'and 2 to be 'a'. 'a' is returned as it is the smaller of the two.
Third layer:
(2, 0) -> In the previous example, we calculated both 2 and 0 to be 'a'. 'a' is returned as is the only char we have.
(2, 1) -> In the previous example, we calculated 2 to be 'a' and 1 to be 'b'. 'a' is returned as it is the smaller of the two.
(2, 2) -> In the previous example, we calculated 2 to be 'a'.'a' is returned as is the only char we have.
The result:
a a a
a b a
a a a
import java.util.*;
import java.io.*;
class Test {
public static void main (String[] args) {
Scanner in = new Scanner(System.in);
int size = in.nextInt();
String[][] arr = new String[size][size];
String resultLine = "";
for(int x = 0; x < size; x ++) {
for(int y = 0; y < size; y ++) {
arr[x][y] = String.valueOf(minChar(x, y, size));
resultLine += arr[x][y] + " ";
}
resultLine += "\n";
}
System.out.println(resultLine);
}
private static int positionToChar(int position, int size) {
return 'a' + (position < size / 2 ? position : size - position - 1);
}
private static char minChar(int x, int y, int size) {
return (char)Math.min(positionToChar(x, size), positionToChar(y, size));
}
}

Related

Printing a squares triangle. How to mirror numbers?

So I've been working on this lab for a while now for my programming class and so far I think I'm on the right track.
However, I'm not quite sure how to mirror the numbers. So pretty much, my code is only printing the top half of the triangle. Anyway here is the actual assignment that was given to us:
Write a program using a Scanner that asks the user for a number n between 1 and 9 (inclusive). The program prints a triangle with n rows. The first row contains only the square of 1, and it is right-justified. The second row contains the square of 2 followed by the square of 1, and is right justified. Subsequent rows include the squares of 3, 2, and 1, and then 4, 3, 2 and 1, and so forth until n rows are printed.
Assuming the user enters 4, the program prints the following triangle to the console:
1
4 1
9 4 1
16 9 4 1
9 4 1
4 1
1
For full credit, each column should be 3 characters wide and the values should be right justified.
Now here is what I have written for my code so far:
import java.util.Scanner;
public class lab6 {
public static void main(String[] args) {
Scanner kybd = new Scanner(System.in);
System.out.println(
"Enter a number that is between 1 and 9 (inclusive): ");
// this is the value that the user will enter for # of rows
int rows = kybd.nextInt();
for (int i = rows; i > 0; i--) {
for (int j = rows; j > 0; j--)
System.out.print((rows - j + 1) < i ?
" " : String.format("%3d", j * j));
System.out.println();
}
}
}
And this is what that code PRINTS when I enter 4:
Enter a number that is between 1 and 9 (inclusive):
4
1
4 1
9 4 1
16 9 4 1
As you can see, I can only get the TOP half of the triangle to print out. I've been playing around trying to figure out how to mirror it but I can't seem to figure it out. I've looked on this website for help, and all over the Internet but I can't seem to do it.
Answer is:
public static void main(String... args) {
Scanner kybd = new Scanner(System.in);
System.out.println("Enter a number that is between 1 and 9 (inclusive): ");
int rows = kybd.nextInt(); // this is the value that the user will enter for # of rows
for (int i = -rows + 1; i < rows; i++) {
for (int j = -rows; j < 0; j++)
System.out.print(abs(i) > j + rows ? " " : String.format("%3d", j * j));
System.out.println();
}
}
Try think of this as how to find points(carthesians) that are betwean three linear functions(area of triangle that lied betwean):
y = 0 // in loops i is y and j is x
y = x + 4
y = -x -4
And here is example result for 4:
And 9:
In the outer loop or stream you have to iterate from 1-n to n-1 (inclusive) and take absolute values for negative numbers. The rest is the same.
If n=6, then the triangle looks like this:
1
4 1
9 4 1
16 9 4 1
25 16 9 4 1
36 25 16 9 4 1
25 16 9 4 1
16 9 4 1
9 4 1
4 1
1
Try it online!
int n = 6;
IntStream.rangeClosed(1 - n, n - 1)
.map(Math::abs)
.peek(i -> IntStream.iterate(n, j -> j > 0, j -> j - 1)
// prepare an element
.mapToObj(j -> i > n - j ? " " : String.format("%3d", j * j))
// print out an element
.forEach(System.out::print))
// start new line
.forEach(i -> System.out.println());
See also: Output an ASCII diamond shape using loops
Another alternative :
public static void main(String args[]) {
Scanner kybd = new Scanner(System.in);
System.out.println("Enter a number that is between 1 and 9 (inclusive): ");
int rows = kybd.nextInt(); // this is the value that the user will enter for # of rows
int row = rows, increment = -1;
while (row <= rows){
for (int j = rows; j > 0; j--) {
System.out.print(rows - j + 1 < row ? " " : String.format("%3d", j * j));
}
System.out.println();
if(row == 1) {
increment = - increment;
}
row += increment;
}
}
The outer loop from 1-n to n-1 inclusive, and the inner decrementing loop from n to 0. The if condition is the absolute value of i should not be greater than n - j.
Try it online!
int n = 6;
for (int i = 1 - n; i <= n - 1; i++) {
for (int j = n; j > 0; j--)
if (Math.abs(i) > n - j)
System.out.print(" ");
else
System.out.printf("%3d", j * j);
System.out.println();
}
Output:
1
4 1
9 4 1
16 9 4 1
25 16 9 4 1
36 25 16 9 4 1
25 16 9 4 1
16 9 4 1
9 4 1
4 1
1
See also: Invert incrementing triangle pattern

programming puzzle : how to count number of bacteria that are alive?

Recently, I had encountered an interesting programming puzzle which had some good twist and turn mentioned in the puzzle. Below the question which amazed me, I simply eager to know if any relevant solution probably in java is feasible for below scenario.
Problem statement:
There is a grid of dimension m*n, initially, a bacterium is present at the bottom left cell(m-1,0) of the grid with all the other cells empty. After every second, each bacteria in the grid divides itself and increases the bacteria count int the adjacent(horizontal,vertical and diagonal) cells by 1 and dies.
How many bacteria are present at the bottom right cell(m-1,n-1) after n-1 seconds?
I had taken references from
https://www.codechef.com/problems/BGH17
but failed to submit the solution
Below is the image for more insite of problem
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
import java.util.Stack;
public class BacteriaProblem {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
System.out.println("Number of Rows: ");
int m = sc.nextInt();
System.out.println("Number of Columns: ");
int n = sc.nextInt();
int[][] input = new int[m][n];
input[m - 1][0] = 1;
Stack<String> stack = new Stack<>();
stack.push(m - 1 + "~" + 0);
reproduce(stack, input, n - 1);
System.out.println("Value at Bottom Right corner after n-1 secs: " + input[m - 1][n - 1]);
}
private static void reproduce(Stack<String> stack, int[][] input, int times) {
//exit condition
if (times < 1) {
return;
}
//bacteria after splitting
List<String> children = new ArrayList<>();
//reproduce all existing bacteria
while (!stack.isEmpty()) {
String[] coordinates = stack.pop().split("~");
int x = Integer.parseInt(coordinates[0]);
int y = Integer.parseInt(coordinates[1]);
for (int i = -1; i <= 1; i++) {
for (int j = -1; j <= 1; j++) {
if (i == 0 && j == 0) continue;
split(input, x + i, y + j, children);
}
}
input[x][y]--;
}
//add all children to stack
for (String coord : children) {
stack.push(coord);
}
//reduce times by 1
reproduce(stack, input, times - 1);
}
private static void split(int[][] input, int x, int y, List<String> children) {
int m = input.length;
int n = input[0].length;
if (x >= 0 && x < m && y >= 0 && y < n) {
input[x][y]++;
children.add(x + "~" + y);
}
}
}
Well, I was asked this question in an Online Hackerrank test and couldn't solve it at that time.
I did later try to code it and here's the soln in C++,
long countBacteriasAtBottomRight(int m, int n){
long grid[m][n];
// Set all to 0, and only bottom left to 1
for (int i=0; i<m; i++){
for (int j=0; j<n; j++){
grid[i][j] = 0;
}
}
grid[m-1][0] = 1;
// Start the cycle, do it for (n-1) times
int time = n-1;
vector<long> toBeUpdated;
while (time--){
cout << "\n\nTime: " << time;
for (int i=0; i<m; i++){
for (int j=0; j<n; j++){
while (grid[i][j] > 0){
grid[i][j]--;
// upper left
if (i > 0 && j > 0){
toBeUpdated.push_back(i-1);
toBeUpdated.push_back(j-1);
}
// upper
if (i > 0){
toBeUpdated.push_back(i-1);
toBeUpdated.push_back(j);
}
// upper right
if (i > 0 && j < n-1){
toBeUpdated.push_back(i-1);
toBeUpdated.push_back(j+1);
}
// left
if (j > 0){
toBeUpdated.push_back(i);
toBeUpdated.push_back(j-1);
}
// bottom left
if (i < m-1 && j > 0){
toBeUpdated.push_back(i+1);
toBeUpdated.push_back(j-1);
}
// bottom
if (i < m-1){
toBeUpdated.push_back(i+1);
toBeUpdated.push_back(j);
}
// bottom right
if (i < m-1 && j < n-1){
toBeUpdated.push_back(i+1);
toBeUpdated.push_back(j+1);
}
// right
if (j < n-1){
toBeUpdated.push_back(i);
toBeUpdated.push_back(j+1);
}
};
}
}
// Update all other cells
for (int k=0; k<toBeUpdated.size(); k+=2){
grid[toBeUpdated[k]][toBeUpdated[k+1]]++;
}
for (int i=0; i<m; i++){
cout << endl;
for (int j=0; j<n; j++)
cout << grid[i][j] << " ";
}
// Clear the temp vector
toBeUpdated.clear();
};
return grid[m-1][n-1];
}
The starting situation only has a value in the left-most column 0. We need to know the situation in the right-most column n-1 after time n-1. This means that we only have to look at each column once: column x at time x. What happens to column x after time x is no longer important. So we go from left to right, adding up the cells from the previous column:
1
1 8
1 7 35
1 6 27 104
1 5 20 70 230
1 4 14 44 133 392
1 3 9 25 69 189 518
1 2 5 12 30 76 196 512
1 1 2 4 9 21 51 127 323 ...
You will also notice that the result for the last cell is only influenced by two cells in the previous column, and three in the one before that, so to calculate the end result for e.g. the case n=9, you only need to calculate the values in this triangle:
1
1 4 14
1 3 9 25 69
1 2 5 12 30 76 196
1 1 2 4 9 21 51 127 323
However high the grid is, we only ever have to go up n/2 (rounded up) rows. So the total number of sums we have to calculate is n2/4, or n×m if m < n/2.
Also note that we don't have to store all these values at once, because we go column by column from left to right. So we only need a one-dimensional array of size n/2, and the current values in it are transformed like this (e.g. going from column 4 to 5 in the example above):
[4, 5, 3, 1] (0) -> 0 + 5 - 0 = 5
[9, 5, 3, 1] (5) -> 9 + 3 - 5 = 7
[9,12, 3, 1] (7) -> 12 + 1 - 7 = 6
[9,12, 9, 1] (6) -> 9 + 0 - 6 = 3
[9,12, 9, 4] (3) -> 4 + 0 - 3 = 1
[9,12, 9, 4, 1] (1) (additional value is always 1)
where we iterate over the values from left to right, add up the value to the left and right of the current element, subtract a temporary variable which is initialized to 0, store the result in a temporary variable, and add it to the current element.
So the theoretical time complexity is O(n2) or O(n.m) and the space complexity is O(n) or O(m), whichever is smaller. In real terms, the number of steps is n2/4 and the required space is n/2.
I don't speak Java, but here's a simple JavaScript code snippet which should easily translate:
function bacteria(m, n) {
var sum = [1];
for (var col = 1; col < n; col++) {
var temp = 0;
var height = Math.min(col + 1, n - col, m);
if (height > sum.length) sum.push(0);
for (var row = 0; row < height; row++) {
var left = row > 0 ? sum[row - 1] : 0;
var right = row < sum.length - 1 ? sum[row + 1] : 0;
temp = left + right - temp;
sum[row] += temp;
}
}
return sum[0];
}
document.write(bacteria(9, 9));

Magic square code loop

This is the code for a method which creates a magic square. n is the length of the square. It has to look like:
static int[][] magicSquare(int n) {
int[][] square=new int[n][n];
I don't understand this k=(k+1)%n; especially, why is it %n ?? Doesn´t that put k to 1 every loop again?
for (int i=0; i<n; i++){
in k=i;
for (int j=0; j<n; j++){
square[i][j]=k+1;
k=(k+1)%n;
1 2 3 4
2 3 4 1
3 4 1 2
4 1 2 3
The % in Java is used for modular division. Whenever the operator is applied the right-hand operand will be subtracted as many times as it can from the left-hand operand and what's left will be the output. You can easily check it by dividing the left-hand operand by the right-hand operand and take the leftover as an integer. In the case of a%b it will be like
a - (a/b)*b.
here are some examples:
10 % 4 = 2 // 2*4 = 8 + 2 = 10
10 % 5 = 0 // 2*5 = 10 + 0 = 10
0 % 4 = 0 // result here is 0 thus 0*4 = 0 + 0 = 0
// if you try to extract 4 from 0, you will not succeed and what's left will be returned (which was originally 0 and it's still 0)...
In your case:
k = (k + 1) % n;
is assuring that the value of k will never exceed 4, thus if it is dividable by 4 then it will be divided and the leftover will be written there. In the case when k is exactly 4 you will have the value of 0 written down into k but since you are always adding k + 1 it is writing the value of 1.
For beginners I do recommend to print the values you are interested in and observe how do the data migrate. Here I've added some printlns for you just to get the idea. Run the code and test it yourself. I do believe the things are going to be a bit cleaner.
public static void main(String[] args) {
int n = 4;
int[][] square = new int[n][n];
System.out.println("--------------");
for (int i = 0; i < n; i++) {
int k = i;
System.out.println("Filling magic cube line " + (i + 1) + ". The k variable will start from " + i + "."); // i initial value is 0 so we add 1 to it just to get the proper line number.
for (int j = 0; j < n; j++) {
System.out.println("Filling array index [" + i + "][" + j + "] = " + (k + 1)); // array indexes start from 0 aways and end at array.length - 1, so in case of n = 4, last index in array is 3.
square[i][j] = k + 1; // add 1 to k so the value will be normalized (no 0 entry and last entry should be equal to n).
k = (k + 1) % n; // reset k if it exceeds n value.
}
System.out.println("--------------");
}
Arrays.stream(square).forEach(innerArray -> {
Arrays.stream(innerArray).forEach(System.out::print);
System.out.println();
});
}
You could always play around and refactor the code as follows:
public static void main(String[] args) {
int n = 4;
int[][] square = new int[n][n];
System.out.println("--------------");
for (int i = 1; i <= n; i++) {
int k = i;
System.out.println("Filling magic cube line " + i + ". The k variable will start from " + i + ".");
for (int j = 0; j < n; j++) {
System.out.println("Filling array index [" + (i - 1) + "][" + (j - 1) + "] = " + k); // array indexes start from 0 aways and end at array.length - 1, so in case of n = 4, last index in array is 3. Subtract both i and j with 1 to get the proper array indexes.
square[i - 1][j - 1] = k;
k = (k + 1) % n; // reset k if it exceeds n value.
}
System.out.println("--------------");
}
Arrays.stream(square).forEach(innerArray -> {
Arrays.stream(innerArray).forEach(System.out::print);
System.out.println();
});
}
Remember that the array's indexing starts from 0 and ends at length - 1. In the case of 4, the first index is 0 and the last one is 3. Here is the diff of two implementations, try to see how does the indexes and values depends both on the control variables i and j.
https://www.diffchecker.com/x5lIWi4A
In the first case i and j both start from 0 and are growing till they it's values are both less than n, and in the second example they start from 1 and are growing till they are equal to n. I hope it's getting clearer now. Cheers

How to print a diamond of random numbers?

Can someone help me complete this numeric diamond? I have the right side of the diamond printing out, but I'm having trouble printing out the left side of it. If anybody can help I would really appreciate it.
I made some changes to my code. I now need my code to print one column in the middle of the diamond instead of two.
public class NumericDiamond {
public static void main(String[] args) {
/*
1 1
4 3 4 2
4 4 5 7 4 3
5 3 5 4
4 5
*/
int noOfColumns = 1;
int noOfSpaces = 3;
int start = 0;
for (int i = 1; i <= 5; i++) {
for (int j = noOfSpaces; j >= 1; j--) {
System.out.print(" ");
}
for (int j = 1; j <= noOfColumns; j++) {
System.out.print(noOfColumns);
}
if (i < 5) {
start = i;
} else {
start = 8 - i;
}
System.out.print(start + " ");
start--;
System.out.println();
if (i < 3) {
noOfColumns = noOfColumns + 2;
noOfSpaces = noOfSpaces - 1;
} else {
noOfColumns = noOfColumns - 2;
noOfSpaces = noOfSpaces + 1;
}
}
}
}
When you write something out to the screen, think in rows.
In the first and last row, you print 1 random number. In the second and fourth row, you print 3 random numbers. In the middle row, you print 5 random numbers.
You can use tab or spaces to place the numbers to their positions.
Random rnd = new Random();
for(int i = 0; i < 5; i++) {
if(0 == i || 4 == i) System.out.println("\t\t" + (rnd.nextInt(5)+1) + "\t\t\t" + (i+1));
if(1 == i || 3 == i) System.out.println("\t" + (rnd.nextInt(5)+1) + "\t" + (rnd.nextInt(5)+1) + "\t" + (rnd.nextInt(5)+1) + "\t\t" + (i+1));
if(2 == i) System.out.println((rnd.nextInt(5)+1) + "\t" + (rnd.nextInt(5)+1) + "\t" + (rnd.nextInt(5)+1) + "\t" + (rnd.nextInt(5)+1) + "\t" + (rnd.nextInt(5)+1) + "\t" + (i+1));
}
Something like this.
To print a diamond you can use two nested for loops (or streams) over rows and columns from -n to n. The diamond shape is obtained when n > iAbs + jAbs. The value of a cell depends on its coordinates i and j, or it can be some kind of constant or random value:
int n = 5;
for (int i = -n; i <= n; i++) {
// absolute value of 'i'
int iAbs = Math.abs(i);
for (int j = -n; j <= n; j++) {
// absolute value of 'j'
int jAbs = Math.abs(j);
// diamond shape (cell value = iAbs + jAbs)
if (iAbs + jAbs > n) {
System.out.print(" ");
} else {
System.out.print(" " + (iAbs + jAbs));
}
}
System.out.println(" i=" + iAbs);
}
Output:
5 i=5
5 4 5 i=4
5 4 3 4 5 i=3
5 4 3 2 3 4 5 i=2
5 4 3 2 1 2 3 4 5 i=1
5 4 3 2 1 0 1 2 3 4 5 i=0
5 4 3 2 1 2 3 4 5 i=1
5 4 3 2 3 4 5 i=2
5 4 3 4 5 i=3
5 4 5 i=4
5 i=5
Similarly, you can use two nested streams:
int n = 5;
IntStream.rangeClosed(-n, n)
// absolute value of 'i'
.map(Math::abs)
.peek(i -> IntStream.rangeClosed(-n, n)
// absolute value of 'j'
.map(Math::abs)
// diamond shape (cell value = n - i - j)
.mapToObj(j -> i + j > n ? " " : " " + (n - i - j))
.forEach(System.out::print))
.mapToObj(i -> " i=" + i)
.forEach(System.out::println);
Output:
0 i=5
0 1 0 i=4
0 1 2 1 0 i=3
0 1 2 3 2 1 0 i=2
0 1 2 3 4 3 2 1 0 i=1
0 1 2 3 4 5 4 3 2 1 0 i=0
0 1 2 3 4 3 2 1 0 i=1
0 1 2 3 2 1 0 i=2
0 1 2 1 0 i=3
0 1 0 i=4
0 i=5
See also:
• Drawing numeric diamond
• Diamond with nested for loops

Why are my map values incorrect?

String a = "Some small sample text!";
char[] letters = a.toCharArray();
int[] charvals = new int[letters.length];
for (int i = 0; i<letters.length;i++) {
int curr = (int) letters[i];
charvals[i] = curr;
}
HashMap<Character, Integer> lettermap = new HashMap<Character, Integer>();
Character c;
for (int i = 0; i<letters.length; i++) {
c = letters[i];
if (lettermap.containsKey(c)) {
lettermap.put(c, lettermap.get(c) + 1); }
else {
lettermap.put(c, 1); }}
for (int i = 0; i < charvals.length; i++) {
if (charvals[i] !=32) {
c = letters[i];
System.out.println(lettermap.get(c));
}
1 1 3 3 2 3 2 3 3 2 2 3 1 3 3 2 3 1 2 1
This is the output, horizontally for space concerns. I should only have 3 "3s" or letters that appear 3 or more times, but I get 9. Can anybody tell me why?
It is easy to see on the 3rd item of output. The key is 'm' in my String and it is the first time it is appearing in the map yet the value is 3 and not 1. Why is this happening?
for (int i = 0; i < charvals.length; i++) {
if (charvals[i] !=32) {
c = letters[i];
System.out.println(lettermap.get(c));
}
This goes through every character in the original string -- not uniqued -- and prints outs its count in the map. So if there are three 'c's in the string, it'll print out the count (3) for 'c' three times.
You probably want to iterate over lettermap.entrySet() instead.
Your algorithm is ok really, the only problem is in the output. You are taking individual characters of your input string and outputting their counts, like this:
S o m e s m a l l s a m p l e t e x t
1 1 3 3 2 3 2 3 3 2 2 3 1 3 3 2 3 1 2
Try using lettermap.keySet() instead:
for (Character c2 : lettermap.keySet()) {
System.out.printf("%s - %s\n", c2, lettermap.get(c2));
}
Your program currently only outputs the final counts for the characters present in your String.
To print a running total, you would print the value present in the Map after the value is changed by adding a print statement to your second for loop, like so:
for (int i = 0; i < letters.length; i++) {
c = letters[i];
if (lettermap.containsKey(c)) {
lettermap.put(c, lettermap.get(c) + 1);
} else {
lettermap.put(c, 1);
}
System.out.print(lettermap.get(c) + " ");
}
This prints the following output: 1 1 1 1 1 1 2 1 1 2 2 2 2 3 1 3 2 3 1 3 1 2 1
If you then add some logic to print the character that is being counted, the following is returned:
{'S'=1, 'o'=1, 'm'=1, 'e'=1, ' '=1, 's'=1, 'm'=2, 'a'=1, 'l'=1, 'l'=2, ' '=2, 's'=2, 'a'=2, 'm'=3, 'p'=1, 'l'=3, 'e'=2, ' '=3, 't'=1, 'e'=3, 'x'=1, 't'=2, '!'=1}
Just going to leave this here for anyone interested:
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
public class CharacterCount {
public static void main(String[] args) {
print("Some small sample text!");
}
public static void print(String str) {
HashMap<Character, Integer> map = new HashMap<Character, Integer>();
for (Character c : str.toCharArray()) {
map.put(c, 1 + (map.containsKey(c) ? 1 : 0));
}
List<Character> cList = new ArrayList<Character>(map.keySet());
Collections.sort(cList);
for (Character c : cList) {
System.out.printf("'%c' - %d%n", c, map.get(c));
}
}
}
Prints:
' ' - 2
'!' - 1
'S' - 1
'a' - 2
'e' - 2
'l' - 2
'm' - 2
'o' - 1
'p' - 1
's' - 2
't' - 2
'x' - 1

Categories

Resources