I am trying to write a program that will, when executed, will go through an array and remove all instances of开发者_运维技巧 0.0 and change the size of the array equal to the number of non zero elements and put those elements in their previous order. That is, if n=10 and the contents of a[j], j = 0 to n - 1 are initially
0.0, 1.2, 0.0, 0.0, 0.0, 2.3, 0.0, 9.7, 5.6, 0.0
then after execution of the code the contents should be
n=4, a[0]=1.2, a[1]=2.3, a[2]=9.7, and a[3]=5.6.
This is what I have so far:
import java.util.Scanner;
public class hw2
{
public static void main(String[] args)
{
Scanner scan = new Scanner(System.in);
final double KEY = 0.0;
int n = scan.nextInt();
double[] a = new double[n];
for(int i=0; i<n; i++)
{
a[i] = scan.nextDouble();
}
for(int k = 0; k<n; k++)
{
if(a[k] == KEY)
{
a[k] = a[k+1];
n--;
}
System.out.println(a[k]);
}
}
}
Just a little nudge in the right direction would be appreciated.
Consider using an ArrayList, which will allow you to add items when you want, grow as needed, and maintain an accurate count.
Although in this case, if you wanted/needed to use an array, you could simply not save the value if it's "0", perhaps. (Also don't increment the "used array variable", except when you add, so you know how much contains "non 0" data or treat the first "0" encountered during iteration as "end of useful data" -- arrays are initialized with the default value of the type.)
If you want to go from an array with zeros to an array with no zeros at all, you must use two passes -- one to count the non-zeros, to construct a new array of the appropriate size, and then copy the non-zero values over. This could be done in reverse as well (compact the initial array, and then copy the "filled" portion of it over), but it's slightly more complicated.
If you do continue with your current approach (which the result array will have zeros, but at the end), you need to maintain two index pointers -- one is the primary loop iterator, the second is the next place to put the non-zero value, which is incremented only when a value is copied (or not moved, as when both indexes are the same, which will be the case until the first 0 is encountered). Make sure to "zero" the place you move the non-zero from. The number of moves can be reduced if order does not need to be preserved.
Your implementation (2nd for loop) is not right, it will fail to simple test case: Input > 5 2.0 2 0.0 3 0.0 Your program will have wrong output: 2.0 2.0 3.0 3.0
but it should be 2.0 2.0 3
Also, you can't use == to compare two double.
The following code is my solution basing on your current code:
public class hw21 {
public static void main(String[] args) {
Scanner scan = new Scanner(System.in);
final double KEY = 0.0;
final Double ACCEPTABLE_TOLERANCE = 0.000000000001d;
int n = scan.nextInt();
double[] a = new double[n];
for (int i = 0; i < n; i++) {
a[i] = scan.nextDouble();
}
for (int k = 0, j = 0; k < n; k++) {
if (Math.abs(a[k] - KEY) < ACCEPTABLE_TOLERANCE) {
continue;
}
a[j] = a[k];
System.out.println(a[j]);
j++;
}
}
}
Also I prefer to use an ArrayList like below:
public class hw2 {
public static void main(String[] args) {
Scanner scan = new Scanner(System.in);
final double KEY = 0.0;
final Double ACCEPTABLE_TOLERANCE = 0.000000000001d;
int n = scan.nextInt();
double[] a = new double[n];
for (int i = 0; i < n; i++) {
a[i] = scan.nextDouble();
}
List<Double> newList = new ArrayList<Double>();
for (int k = 0; k < n; k++) {
if (Math.abs(a[k] - KEY) < ACCEPTABLE_TOLERANCE) {
continue;
}
newList.add(a[k]);
}
System.out.println("There are " + newList.size() + " no-zero double:");
System.out.println(newList);
}
}
import java.util.Arrays;
import java.util.Scanner;
public class StackOverflow1
{
public static final double KEY = 0.0;
private static final Scanner INPUT = new Scanner(System.in);
public static void main(String[] args) {
int length = INPUT.nextInt();
double[] array = new double[length];
for(int i=0; i<length; i++) {
array[i] = INPUT.nextDouble();
}
int index = 0;
for(int k = 0; k < length ; k++) {
if(array[k] == KEY) {
continue;
}
array[index] = array[k]; // bring the non-zeroth element forward
if (index != k) array[k] = 0; //make the non-zeroth element zero in the actual location
index++;
}
System.out.println("n = " + index + " array = " + Arrays.toString(array));
}
}
you can remove those unwanted zeros as follows but in this case it get sorted.
@org.junit.Test
public void test15() throws Exception {
double[] arr = new double[]{0.0,1.1,0.1,0.0,2.1};
double[] nonZeroArr = arr;
Arrays.sort(nonZeroArr);
int index = -1;
while((index = Arrays.binarySearch(nonZeroArr, 0.0)) > -1){
double[] newArr = new double[nonZeroArr.length-index-1];
System.arraycopy(nonZeroArr, index+1, newArr, 0, newArr.length);
nonZeroArr = newArr;
}
for (double d : arr) {
System.out.print(d +",");
}
System.out.println();
for (double d : nonZeroArr) {
System.out.print(d + ",");
}
}
IF you want to sound really smart in class point out that this is a one liner in a lot of languages that are more productive than Java :)
精彩评论