How to change position of the elements in an array - java

I'm writing a program, that take 10 Integers from a keyboard and list them in an array indexed from 0-9, and reports the position of the lowest number in the array. If the lowest number has any other position than 0, then the program is supposed to switch the position of the lowest number input with the number in the first position in the array:
import java.util.Scanner;
public class q35 {
public static void main(String args[]) {
Scanner tastatur = new Scanner(System.in);
int[] helTall = new int[10];
int input;
int lowest = Integer.MAX_VALUE;
for(int i=0;i<helTall.length;i++) {
System.out.println("Integers? ");
input = tastatur.nextInt();
if (input < lowest) {
lowest = input;
}
helTall[i] = input;
}
for (int i = 0; i < helTall.length; i++) {
helTall[0] = lowest;
System.out.println(helTall[i]);
}
System.out.println("Lowest number is " + lowest);
}
}
The only problem is that instead of changing position with the lowest number with the number at helTall[0], it just completely replaces the first number in the sequence helTall[0] with the lowest Integer, that way if my input is 4 5 63 23 6 -4 7 33 23 99, then the output becomes -4 5 63 23 6 -4 7 33 23 99 (as you can see the first input number is completely erased), but it should have been -4 5 63 23 6 4 7 33 23 99 any tips/advice/solutions? Thanks in advance.

You should keep track of the index of the lowest number (each time you write lowest = input; you should add lowestIndex=i;.
Then helTall[lowestIndex] will be the lowest number.
So you swap helTall[lowestIndex] with helTall[0] instead of just overwriting the value of helTall[0].
I thought it was enough to describe the solution in words, but I guess it wasn't...
int lowest = Integer.MAX_VALUE;
int lowestIndex = 0;
for(int i=0;i<helTall.length;i++){
System.out.println("Integers? ");
input = tastatur.nextInt();
if (input < lowest){
lowest = input;
lowestIndex = i;
}
helTall[i]=input;
}
// swap the numbers
if (lowestIndex > 0) {
int temp = lowest;
helTall[lowestIndex] = helTall[0];
helTall[0] = temp;
}
// display output
for (int i = 0; i < helTall.length; i ++) {
System.out.println(helTall[i]);
}

This part is wrong:
for (int i = 0; i < helTall.length; i ++) {
helTall[0]=lowest;
System.out.println(helTall[i]);
}
First, you do not need to repeatedly (10 times) put lowest into helTall[0]. Let's move that outside first so it's only done once:
helTall[0]=lowest;
for (int i = 0; i < helTall.length; i ++) {
System.out.println(helTall[i]);
}
Next, the line we put outside the loop overwrites the helTall[0] without regard for what is already in there. We need to temporarily save that number in there elsewhere, then overwrite the spot, so that we can use it to overwrite the spot where the lowest number was:
int numberAtLocationZero = helTall[0];
helTall[0]=lowest;
// Now, on this line we need to write helTall[lowestNumberIndex] = numberAtLocationZero;
for (int i = 0; i < helTall.length; i ++) {
System.out.println(helTall[i]);
}
In the above code I wrote a comment. It relies on you either knowing where in the array the lowest number was, or to find it again. If you add a new variable to your code that takes in values called lowestNumberIndex and update that each time you detect a new lowest number, then you're pretty much done if you uncomment my comment.

You need a separate variable to store what is in the bottom of the array before you overwrite it with your new lowest input number.
helTall[0]=lowest;
should be proceeded by
int placeholder = helTall[0]
and followed by
hellTall[i] = placeholder;
This way, you'll end up swapping the two array elements, the first swapped with the lowest. Is this what you're trying to accomplish? This leaves most of the array unsorted.

Related

How to count inputs in an array in java

I have n inputs.
these inputs are numbers from 1 to 100.
I want to output the number that appears less than the other ones; also if there are two numbers with the same amount of appearance, I want to output the number that is less than the other one.
I wrote this code but it doesn't work!
Scanner scanner = new Scanner(System.in);
int n=scanner.nextInt(), max=0 , ans=-1;
int[] counter = new int[n];
for(int i=0; i<n; i++)
counter[scanner.nextInt()]+=1;
for(int j=1; j<=100; j++){
if(counter[j]>max)
max=counter[j];
}
for (int i=1; i<=max; i++){
if(counter[i]>0)
if(ans==-1 || counter[ans]>counter[i] || (counter[ans] == counter[i] && i<ans))
ans=i;
}
System.out.print(ans);
There’s a couple of problems with your code, but the main one is the last for loop: You are trying to find the first (ie lowest) number whose counter is equal to max, so your loop should be from 1 to n, not 1 to max.
Another problem is if you are using the number, which is in the range 1-n, as your array index, you need an array of size n+1, not n.
I pinched this from another question regarding the title of yours:
i = input.nextInt (); while (i != 0) { counts [i]++; i = input.nextInt (); } That method increments the number at the position of the user input in the counts array, that way the array holds the number of times a number occurs in a specific index, e.g. counts holds how often 3 occurs.
counter array should contain frequency values for the numbers from 1 to 100 inclusive.
That is, either a shift by 1 should be used when counting the frequency:
int[] counter = new int[100];
for (int i = 0; i < n; i++) {
counter[scanner.nextInt() - 1]++;
}
or 101 may be used as the length of counter array thus representing values in the range [0..100], without shifting by 1.
int[] counter = new int[101];
for (int i = 0; i < n; i++) {
counter[scanner.nextInt()]++;
}
The minimal least frequent number can be found in a single loop (assuming that the counter length is 101).
int minFreq = 101, answer = -1;
for(int j = 1; j <= 100; j++) {
if (counter[j] > 0 && counter[j] < minFreq) { // check valid frequency > 0
minFreq = counter[j];
answer = j;
}
}
System.out.println(answer);
For a wider range of input values (e.g. including negative values) of a relatively small count it is better to use a hashmap instead of a large sparse array.

Program to find majority element of an input array doesn't work

I'm trying to find the majority element using Boyer and Moore approach. The program should ask the user to input "n" number of lines on the first line, then there will be "n" numbers followed "n" lines as input. (Ex: user input 5 on the first line, then there will be 5 numbers followed)
Next, use Boyer and Moore approach to find the majority element of an input array. If the majority element doesn't exist in the input array, then execute -1. My program output shows 0 no matter what input I entered. Would you please check it and correct my program?
Output example:
4
12
12
1
12
12
/Or: 3 11 2 13 -1
public static void main (String[]args)
{
int a[] = new int [1000000];
Scanner sc = new Scanner (System.in);
// User input n number of lines
int numberOfLine = sc.nextInt();
//Loop to have n elements as input
for (int i = 1; i<= numberOfLine; i++)
{
a[i] = sc.nextInt();
}
// Call method to display majority element
getMajorityElement(a);
sc.close();
}
//Method to Find M.E using Boyer & Moore approach
public static void getMajorityElement(int [] array)
{
int majorityElement = array[0];
int count = 1;
for (int index = 1; index<array.length; index++)
{
if(majorityElement==array[index])
{
count++;
}
else if(count==0)
{
majorityElement = array[index];
count = 1;
}
else
{
count --;
}
}
// Check if candidate M.E occur more than n/2 times
count = 0;
for (int index = 0; index<array.length; index++)
{
if(array[index]==majorityElement)
{
count++;
}
}
if (count > array.length/2)
{
System.out.println(majorityElement);
}
else
{
System.out.println("-1");
}
}
The reason you get this behavior is that your array of 1,000,000 elements has a majority element of zero: only the initial three or four items are set, while the rest of the items are occupied by zeros - the default value of an int in Java.
Fix this problem by allocating at size once the length is entered. You also need to fix the code that reads input to make sure that the data ends up at indexes 0..numberOfLine-1:
Scanner sc = new Scanner (System.in);
// User input n number of lines
int numberOfLine = sc.nextInt();
int a[] = new int [numberOfLine];
//Loop to have n elements as input
for (int i = 0 ; i < numberOfLine ; i++) {
a[i] = sc.nextInt();
}

Finding repeats in a 2D array

I have made a program that outputs the number of repeats in a 2D array. The problem is that it outputs the same number twice.
For example: I input the numbers in the 2D array through Scanner: 10 10 9 28 29 9 1 28.
The output I get is:
Number 10 repeats 2 times.
Number 10 repeats 2 times.
Number 9 repeats 2 times.
Number 28 repeats 2 times.
Number 29 repeats 1 times.
Number 9 repeats 2 times.
Number 1 repeats 1 times.
Number 28 repeats 2 times.
I want it so it skips the number if it has already found the number of repeats for it. The output should be:
Number 10 repeats 2 times.
Number 9 repeats 2 times.
Number 28 repeats 2 times.
Number 29 repeats 1 times.
Number 1 repeats 1 times.
Here is my code:
import java.util.Scanner;
public class Repeat
{
static Scanner leopard = new Scanner(System.in);
public static void main(String [] args)
{
final int ROW = 10; //Row size
final int COL = 10; //Column size
int [][] num = new int[ROW][COL];
int size;
//Get input
size = getData(num);
//Find repeat
findRepeats(num, size);
}
public static int getData(int [][] num)
{
int input = 0, actualSize = 0; //Hold input and actualSize of array
System.out.print("Enter positive integers (-999 to stop): ");
//Ask for input
for(int i = 0; i < num.length && input != -999; i++)
{
for(int j = 0; j < num[i].length && input != -999; j++)
{
input = leopard.nextInt();
//Check if end
if(input != -999)
{
num[i][j] = input;
actualSize++;
}
}
}
System.out.println();
return actualSize;
}
public static void findRepeats(int [][] num, int size)
{
int findNum;
int total = 0, row = 0, col = 0;
for(int x = 0; x < size; x++)
{
//Set to number
findNum = num[row][col];
//Loop through whole array to find repeats
for(int i = 0; i < num.length; i++)
{
for(int j = 0; j < num[i].length; j++)
{
if(num[i][j] == findNum)
total++;
}
}
//Cycle array to set next number
if(col < num[0].length-1)
col++;
else
{
row++; //Go to next row if no more columns
col = 0; //Reset column number
}
//Display total repeats
System.out.println("Number " + findNum + " appears " + total + " times.");
total = 0;
}
}
}
I know why it is doing it, but I cannot figure out how to check if the number has already been checked for it to skip that number and go to the next number. I cannot use any classes or code that is not used in the code.
Since you cannot use anything other than this, lets say, basic elements of Java consider this:
Make another temporary 2D array with two columns (or just two separate arrays, personally I prefer this one). On the start of the algorithm the new arrays are empty.
When you take a number (any number) from the source 2D structure, first check if it is present in the first temporary array. If it is, just increment the value (count) in the second temporary array for one (+1). If it is not present in the first tmp array, add it to it and increase the count (+1) in the second at the same index as the newly added number in the first (which should be the last item of the array, basically).
This way you are building pairs of numbers in two arrays. The first array holds all your distinct values found in the 2D array, and the second one the number of appearances of the respective number from the first.
At the and of the algorithm just iterate the both arrays in parallel and you should have your school task finished. I could (and anyone) code this out but we are not really doing you a favor since this is a very typical school assignment.
It's counting the number two times, first time it appears in the code and second time when it appears in the code.
To avoid that keep a system to check if you have already checked for that number. I see you use check int array but you haven't used it anywhere in the code.
Do this,
Put the number in the check list if you have already found the count of it.
int count = 0;
check[count] = findNum;
count++;
Note: You can prefill you array with negative numbers at first in order to avoid for having numbers that user already gave you in input.
Next time in your for loop skip checking that number which you have already found a count for
for(int x = 0; x < size; x++) {
findNum = num[row][col];
if(check.containsNumber(findNUm)) { //sorry there is no such thing as contains for array, write another function here which checks if a number exists in the array
//skip the your code till the end of the first for loop, or in other words then don't run the code inside the for loop at all.
}
}
Frankly speaking I think you have just started to learn coding. Good luck! with that but this code can be improved a lot better. A piece of advice never create a situation where you have to use 3 nested for loops.
I hope that you understood my solution and you know how to do it.
All answers gives you some insight about the problem. I try to stick to your code, and add a little trick of swap. With this code you don't need to check if the number is already outputted or not. I appreciate your comments, structured approach of coding, and ask a question as clear as possible.
public static void findRepeats(int [][] num, int size)
{
int findNum;
int total = 1, row = 0, col = 0;
int [] check = new int[size];
while(row < num.length && col < num[0].length)
{
//Set to number
findNum = num[row][col];
//Cycle array to set next number
if(col < num[0].length-1)
col++;
else
{
row++; //Go to next row if no more columns
col = 0; //Reset column number
}
//Loop through whole array to find repeats
for(int i = row; i < num.length; i++)
{
for(int j = col; j < num[i].length; j++)
{
if(num[i][j] == findNum) {
total++;
//Cycle array to set next number
if(col < num[0].length-1)
col++;
else
{
row++; //Go to next row if no more columns
col = 0; //Reset column number
}
if(row < num.length - 1 && col < num[0].length -1)
num[i][j] = num[row][col];
}
}
}
//Display total repeats
System.out.println("Number " + findNum + " appears " + total + " times.");
total = 1;
}
}
you can use a HashMap to store the result. It Goes like this:
// Create a hash map
HashMap arrayRepeat = new HashMap();
// Put elements to the map
arrayRepeat.put(Number, Repeated);

Histogram - Grade Distribution

A grade text file was provide that has one integer number per line representing a
student’s grade in the class. These numbers are not sorted but they are bound between 0 and 100
(inclusive). Using an array, you must count the frequency of each grade value and print it to the
standard output as a horizontal histogram. You must also label the range of each histogram bar and
allow the user to indicate what size interval they would like the histogram to be made with.
This is my assignment and I'm stuck on how to label the range of each histogram bar and
allow the user to indicate what size interval they would like the histogram to be made with?
How can I fix my code?
My Code:
import java.util.Scanner;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
public class GradeHistogram{
public static void main(String[] args) throws Exception {
Scanner gradeFile = new Scanner(new FileInputStream("grades.txt"));
int counter = 0;
while (gradeFile.hasNextLine()) {
gradeFile.nextLine();
counter++;
}
int[] grades = new int[counter];
System.out.println("Grades loaded!");
System.out.println("What bucket size would you like?");
Scanner output = new Scanner(System.in);
for (int i = 0; i < grades.length; i++) {
grades[i] = Integer.parseInt(output.nextLine());
for ( i = 0; i < grades.length; i++) {
if (grades[i] > 0){
System.out.print(i + " | ");
for (int j = 0; j < grades[i]; j++) {
System.out.print("[]");
}
System.out.println();
}
}
}
}
Ops! Pay attention to the fact that you are currently reusing your variable i inside the loop. Your code may (and probably will) behave unexpectedly due to that. I also believe you are not parsing the file correctly.
You can use an auxiliary array to store the frequency of each grade. Initialize an empty array (fill it up with zeros) and then for each grade you just update the corresponding slot.
The code would be something like this:
// 1. Generate your counting array
// (give it 101 slots to include all grades from 0 to 100)
int gradeFrequency = new int[101];
for (int j = 0; j < 101; j++) {
gradeFrequency[j] = 0;
}
// 2. Parse the file and store the frequency of each grade
while (gradeFile.hasNextLine()) {
// get the grade and add 1 to its counter
int grade = Integer.parseInt(gradeFile.nextLine());
gradeFrequency[grade]++;
}
After that, your gradeFrequency array will contain the frequency of each grade in the range 0 to 100.
When printing the histogram, you can ask the user to enter the interval they wish to see the histogram to, and then just print the corresponding frequencies from the array. The code for this would be something like:
// Retrieve the interval the user wants to see
Scanner s = new Scanner(System.in);
System.out.println("Enter the interval for the histogram (e.g. '0 100'):");
int lowerBound = s.nextInt();
int upperBound = s.nextInt();
// Print the histogram title and 'column headers'
System.out.println();
System.out.println("HISTOGRAM");
System.out.println("Grade\tFrequency");
// For each grade present in the interval, print out its 'label'
// (the assigned grade)
for (int i = lowerBound; i < upperBound; i++) {
System.out.print(i + "\t");
// For each time this grade was assigned to a student,
// print an asterisk
for (int j = 0; j < gradeFrequency[i]; j++) {
System.out.print("*");
}
System.out.println();
}
(Note that I didn't include any error handling for unexpected entries, like negative boundaries, start > end or an upper bound bigger than the array size; I leave it up to you!)
The console after an example execution of this code would be something like this:
Enter the interval for the histogram (e.g. '0 100'):
5 11
HISTOGRAM
Grade Frequency
5 ***
6 *
7 ******
8 *
9 **
10 ******
11 ****
Could I make it clear or do you have any remaining questions? :)

Need help writing numbers in the Reverse ORDER

I need some help with this assignment I've been given. Not asking anyone to do my work but I'm really honestly stuck on how to even do this.
I'm supposed to write a program that prompts the user to enter 10 numbers and then have it write all the numbers in reverse order.
Example:
Enter 10 Numbers: 23 89 21 55 67 89 99 13 98 78
Reverse Order: 78 98 13 99 89 67 55 21 89 23
So far all I have is how to get the user inputs. If anyone can push me in the right direction, i'd be very grateful!
import java.util.*;
public class ReverseNumbers
{
public static void main(String[] args)
{
Scanner keyboard = new Scanner(System.in);
int[] values;
values = new int[10];
//Ask the user to enter 10 integers
System.out.println("Please enter 10 numbers:");
for (int i = 0; i< values.length; i++)
{
values[i] = keyboard.nextInt();
}
int[] reverseNums;
reverseNums = new int[10];
for (int i = (values.length -1); i>= 0; i--)
{
reverseNums[ reverseNums.length -1 -i ] = values[ i ];
System.out.println( reverseNums[ i ] );
}
}
}
If you dont want to store the reversed values
for (int i = (values.length -1); i>= 0; i--)
{
System.out.println( values[ i ] );
}
Your code looks good for reading inputs into values. Now you can loop over that array in reverse and print the values:
for (int i = 0; i < values.length; i++)
System.out.println(values[values.length - i - 1]);
Think about it, when i == 0 it will print values[9] since 10 - 0 - 1 = 9. At the end, when i == 9 it will print values[0] since 10 - 9 - 1 = 0.
As you can see, there is no need for the extra reverseNums array.
PS: If you want, you can combine int[] values; and values = new int[10]; into a single line: int[] values = new int[10];
Read in the whole line as a string using Scanner.nextLine(), and then split it into an array using String.split(" ");. After this, you can simply iterate from the end of the array going backwards and print the numbers.
If it's not an assignment then why not try using http://commons.apache.org/proper/commons-lang/ library
ArrayUtils.reverse(int[] array)
I think your code is creating the array correctly. You are just printing out the numbers in the original order because your second for-loop is iterating over them backwards. You can see the correct result by adding the statement below after the last loop:
System.out.println(java.util.Arrays.toString(reverseNums));
You can also perform the complete task with only one iteration:
Scanner keyboard = new Scanner(System.in);
int[] reverseNums= new int[10];
System.out.println("Please enter 10 numbers:");
for (int i = 0; i< values.length; i++) {
reverseNums[values.length -1 - i] = keyboard.nextInt();
}
System.out.println(java.util.Arrays.toString(reverseNums));
To reverse it:
for (int i = 0; i < values.length; i++)
reverseNums[values.length - i - 1] = values[i];

Categories