How to calculate the alternating sum of two arrays in Java? - java

I have to write a function "alternatingSum(a)" that takes an array of numbers and returns the alternating sum (where the sign alternates from positive to negative or vice versa).
For example:
int[] a = { 5, 3, 8, 4 };
Assert(alternatingSum(a) == 6); // because 5-3+8-4 == 6
So far I have tried to take the array and check to see if the index is odd (not including i=0) then subtract it from the i+1, and if it is even do the same thing except add the two. Am I on the right track with this?
Here is my code:
class foo {
public static int alternatingSum(int[] a){
int sum=0;
for (int i=0;i<a.length;i++){
if (i==0){
sum+=a[0]-a[1];
}
if (i%2 == 0){
sum+=(a[i]+a[i+1]);
}
if (i%2 == 1){
sum+=(a[i]-a[i+1]);
}
}
return sum;
}
public static void testAlternatingSum(){
System.out.println("testing code");
int[] a = { 5, 3, 8, 4 };
assert (alternatingSum(a) == 6); // because 5-3+8-4 == 6
}
public static void main(String[] args){
testAlternatingSum();
}
}

a for loop
I would just keep a boolean flag for even (and toggle it with every loop iteration). If it's an even number, than we're performing addition. But if it's not an even number (it's odd) then we can perform an unary negative operation. That might look something like,
int sum = 0;
boolean even = true;
for (int i = 0; i < a.length; i++) {
sum += even ? a[i] : -a[i];
even = !even
}
return sum;
for-each loop
and you could also use a for-each loop and write it like
boolean even = true;
int sum = 0;
for (int value : a) {
sum += even ? value : -value;
even = !even;
}
return sum;

Easy to read..
int[] alternatingSums(int[] a) {
int sum1 = 0;
int sum2 = 0;
for(int i =0; i < a.length; i++){
if((i % 2) != 1){
sum1 += a[i];
}else{
sum2 += a[i];
}
}
int[] result = {sum1 , sum2};
return result;
}

Related

How can I print out n numbers that satisfy the condition

I have written a code that would return either 1 or 4 as the output, and here it is
public static int findSum(int k) {
int sum = 0;
boolean foundNonZero = false;
for (; k != 0; k /= 10) {
if (foundNonZero) {
sum += (k % 10)*(k % 10);
} else {
foundNonZero = k % 10 != 0;
}
}
return sum;
}
Now, I'm trying to write a function public static long[] firstK(int k) that would return k numbers starting from 0 that would satisfy the condition that findsum = 1.
I'm struggling to understand how to do it, despite reading Java syntax and information. and here is my code so far:
public static long[] firstK(int k) {
while (int x = 0;) {
if (findSum(x) = 1;)
System.out.println(x);
}
I know that int(k) isn't used in this, but I have no idea how to implement it. Any help would be greatly appreciated :)
Thank you,
Dave Shah, MUIC
Maybe something like this:
public static List<Integer> firstK(int k) {
List<Integer> result = new ArrayList<>();
for (int x = 0 ; result.size() < k ; x++)
if (findSum(x) == 1)
result.add(k);
return result;
}
If you really want an array rather than a List, I would still use a List to compute the result. I would then create an array from that list and return that as the function's result to have the function return a int[] or long[]. I can't see why you'd want to return long[] or List<Long> rather than int[] or List<Integer>, I doubt the code involved would ever be given the chance to iterate past the maximum integer value.
UPDATE: Here's a complete example that uses an array throughout:
public class Test {
public static int findSum(int k) {
int sum = 0;
boolean foundNonZero = false;
for (; k != 0; k /= 10) {
if (foundNonZero) {
sum += (k % 10)*(k % 10);
} else {
foundNonZero = k % 10 != 0;
}
}
return sum;
}
public static long[] firstK(int k) {
long[] result = new long[k];
int i = 0;
for (int x = 0; i < k; x++)
if (findSum(x) == 1)
result[i++] = x;
return result;
}
public static void main(String[] args) {
long[] r = firstK(5);
System.out.println(Arrays.toString(r));
}
}
Result:
[11, 12, 13, 14, 15]
The use of an array during the operation is fine because you do know the size of that array up front. You often don't, in which case it is usually cleaner to use a List to collect terms, and then convert to an array at the end. I did it this way initially out of habit. In practice, at least in my case, I pretty much never use arrays due to them being less flexible. They ARE more compact and can perform better, but it is rarely the case that the difference matters.

(How) Can I make this Array code look better? (Codingbat - Array-1 sum2)

I'm new to this forum and to programming and I have my first question :)
The objective is to return the sum of the first two integers in the array. My solution is in the picture I've added. Is there a way to solve this with less if cases? (I know I did not have to do the for loop, but I just learned it and wanted to try it out :D)
Thank you for all answers!
https://i.stack.imgur.com/hx06s.png
Edit: Here's my code:
public int sum2(int[] nums) {
int sum = 0;
if(nums.length == 0){
return sum;
}
if(nums.length == 1){
return nums[0];
}
for(int i = 0; i < 2; i++){
sum += nums[i];
}
return sum;
}
you can use limit() method in stream
public long sum2(int[] nums) {
return Arrays.stream(nums).limit(2).sum();
}
You can handle it in this simple way:
public int sum2(int[] nums) {
if (nums.length == 0)
return 0;
if (nums.length == 1)
return nums[0];
return nums[0] + nums[1];
}
You can't remove the two if statements form the code, unless you want to unnecessarily complicate it, for example, as #axurefrog wrote in his comment:
public int sum2(int[] nums) {
int sum = 0;
for (int i = 0; i < nums.length && i < 2; i++)
sum += nums[i];
return sum;
}
This returns the sum of the first n value of the array:
public int sum(int[] arr, int n) {
int sum = 0;
int num = Math.min( arr.length, n );
for( int i=0; i < num; i++ ) {)
sum += arr[i];
}
return sum;
}
Here are two alternative solutions which somewhat look "better":
sum2() with switch so no if statements
sum3() with nested ternary expressions, makes it very short.
It's good practice to avoid multiple return so you can keep the single entry - simple exit point of the algorithm, supporting debugging.
I've left the snippet wrapped up so you can try them by a single copy/paste.
public class Main{
public static int sum2(int[] nums) {
int sum = 0;
switch (nums.length) {
case 0:
break;
case 1:
sum = nums[0];
break;
default:
sum = nums[0] + nums[1];
break;
}
return sum;
}
public static int sum3(int[] nums) {
return nums.length == 1 ? nums[0] : nums.length >= 2 ? nums[0] + nums[1] : 0;
}
public static void main(String []args){
int[] nums1 = {11, 13, 1, 0}; // expected: 24
int[] nums2 = {3}; // expected: 3
int[] nums3 = {}; // expected: 0
System.out.println("sum2: " + sum2(nums1));
System.out.println("sum2: " + sum2(nums2));
System.out.println("sum2: " + sum2(nums3));
System.out.println(' ');
System.out.println("sum3: " + sum3(nums1));
System.out.println("sum3: " + sum3(nums2));
System.out.println("sum3: " + sum3(nums3));
}
}
The output:
sum2: 24
sum2: 3
sum2: 0
sum3: 24
sum3: 3
sum3: 0
You can simply do this without if-else headache
public int sum2(int[] nums)
{
int sum = 0;
for(int i = 0; i < nums.length && i < 2; i++) sum+=nums[i];
return sum;
}
Edit:
Adding i < nums.length in for loop condition to take care of empty array as per comment from Luca Murra
If you're using Java8 or above, and want to have a more generic solution (meaning sum of N numbers) you can use streams as follow:
public long sum2(int[] nums) {
return Arrays.stream(nums).sum();
}

Java Array Manipulation and Recursion

So I have spent a considerable amount of time struggling to comprehend what is wrong with my code. I have an example program that I compared mine to, which works. My code is structured differently (it's all in one method, as requested by my professor) than the example (which uses two methods). I'm supposed to create a a recursive, divide-and-conquer solution to count inversions in an int array.
I am lost on why the example program maintains the manipulations to the input array throughout the recursion, while mine does not. I know Java is pass-by-value, so I am confused why the example works. Any help with me understanding the differences in these solutions would be greatly appreciated! Thanks!
Example code with two methods - merge and invCounter:
public static long merge(int[] arr, int[] left, int[] right) {
int i = 0, j = 0, count = 0;
while (i < left.length || j < right.length) {
if (i == left.length) {
arr[i+j] = right[j];
j++;
} else if (j == right.length) {
arr[i+j] = left[i];
i++;
} else if (left[i] <= right[j]) {
arr[i+j] = left[i];
i++;
} else {
arr[i+j] = right[j];
count += left.length-i;
j++;
}
}
return count;
}
//the recursive function
public static long invCounter(int[] arr) {
int sum = 0;
if (arr.length < 2)
return 0;
int m = (arr.length + 1) / 2;
int left[] = Arrays.copyOfRange(arr, 0, m);
int right[] = Arrays.copyOfRange(arr, m, arr.length);
sum += invCounter(left);
sum += invCounter(right);
sum += merge(arr, left, right);
return sum;
}
My single-method implementation (attempt):
public static int invCounter(int ranking[]) {
int sum = 0;
int result[] = new int[ranking.length];
int resIndx = 0;
if (ranking.length < 2) {
return 0; //base case
}
//divide
int left[] = Arrays.copyOfRange(ranking, 0, ranking.length/2);
int right[] = Arrays.copyOfRange(ranking, ranking.length/2,
ranking.length);
sum += invCounter(left);
sum += invCounter(right);
int i = 0, j = 0;
while (i < left.length || j < right.length) {
if (i == left.length) {
//i empty, just add j
result[resIndx++] = right[j++];
}
else if (j == right.length) {
//j empty, just add i
result[resIndx++] = left[i++];
}
else if (right[j] < left[i]) {
//inversion
result[resIndx++] = right[j++];
sum += left.length - i;
}
else {
//no inversion
result[resIndx++] = left[i++];
}
}
ranking = Arrays.copyOf(result, result.length);
return sum;
}
Why is the example program able to maintain an updated array through the recursion while mine is not?
UPDATE (10/22/15):
So I discovered that I am able to get the correct results if I replace result with ranking and just modify this array directly. My question now though is why can't I use the result array to temporarily store the results and then copy them into the ranking (argument) array at the end? This seems to me like it would be doing the same exact thing as putting the values in earlier, however the changes to ranking aren't reflected if I change it at the end.
Your method doesn't modify the rankings parameter, instead it creates a new int array (result), and you work on it. Try directly set value on the rankings array, not on result array, or simply set the result variable to the rankings.
public static int invCounter(int ranking[]) {
int sum = 0;
int result[] = ranking;
//other code...
Edit: Or you can copy it's content, but not with Arrays.copyOf, because it first CREATES a new array and then copy into it. Use instead System.arrayCopy which copies into an EXISTING array:
System.arrayCopy(result, 0, rankings, 0, result.length();

Cycle through an int array and the use of modulo within it

I need to implement a method that returns the alternating sum of all elements with odd indexes minus the sum of all elements with even indexes. The total sum returned should be -1. 1 - 4 + 9 - 16 + 9 = -1.
Here is my code:
public class Arrays
{
public static void main(String[] args){
int [] data = {1 ,4, 9, 16, 9};
oddAndEven(data);
}
public static int[] oddAndEven(int[] data){
int sum = 0;
int sumA = 0;
int index = data.length;
for(int i:data){
if(index % sumA == 1){
sum = sum-i;
}
else{
sum = sum+i;
}
}
System.out.println(sum);
return sum;
}
}
Can someone tell me where I am going wrong please?
This is a class session, so forgive my basic code and errors.
This is how I would do it:
public class test {
public static void main(String[] args) {
int [] data = {1 ,4, 9, 16, 9};
oddAndEven(data);
}
public static void oddAndEven(int[] data) {
int total = 0;
for (int i = 0; i < data.length; i++)
{
if (i%2==0)
total = total + data[i];
else
total = total - data[i];
}
System.out.println(total);
}
I've gotten rid of the return in the method and changed it to void (as you are printing out the result within it, so there is no need to return it.
You don't need the two different sum values, or the length of the array stored.
The total value is used and set to 0. The for loop then goes through the length of the array. The %2 divides the number by 2 and determines the remainder. So for the first loop, it will calculate 0/2 and work out the remainder (obviously 0). As it ==0, the first if statement in the for loop is executed (adding the numbers).
The second time through, it calculates 1/2, which is 0 with 1 remaining - so the else statement is executed and so on.
Additionally, note how I've gotten rid of the braces around the if and else statements. As long as these statements are a single line, the braces aren't needed - taking the out tends to make the program easier to read (in my opinion). Obviously, if more than one line were needed under them, the braces need to be readded.
What about this ?
public class ArrayMeNow {
public static void main(String[] args) {
int [] data = {1 ,4, 9, 16, 9};
int result = oddAndEven(data);
System.out.println(result);
}
private static int oddAndEven(int[] data) {
int multiplier = 1;
int result = 0;
for(int v:data){
result += v * multiplier;
multiplier *= -1;
}
return result;
}
}
public static int oddAndEven(int[] data) {
int sum = 0;
for (int i=0;i<data.length;i++) {
if (i % 2 == 1) {
sum = sum - data[i];
} else {
sum = sum + data[i];
}
}
System.out.println(sum);
return sum;
}
for(int i:data) doesn't change the value of index. And sumA is supposed to be 2.
Change your for-loop to something like:
for (int i = 0; i < data.length; i++)
if (i % 2 == 1)
sum -= data[i];
else
sum += data[i];
You have to return sum which is of type int NOT int[]. Here is another way to do it.
public static int doAlternateAddSubOn(int[] array) {
int sum = 0;
for(int i=0; i<array.length; i++) {
// When index 'i' is Even, the position is Odd
sum = (i%2==0) ? sum+array[i] : sum-array[i];
}
return sum;
}

Find the first occurrence of an odd and count them

import java.util.*;
public class FirstOddOccurrence {
public static void main(String[] args) {
int[] x = {2, 4, 6, 7, 4, 3, 2, 7, 6, 7, 7};
int i;
display(x);
System.out.printf("# Occurrences of first odd = %3d\n", firstOddCount(x));
}
private static void display(int[] x) {
int i;
System.out.print("Array: ");
for (i = 0; i < x.length; i++) {
if (i < x.length - 1)
System.out.printf("%3d, ", x[i]);
else
System.out.printf("%3d\n", x[i]);
}
}
public static int odd(int[] x) {
int i;
int y;
for (i = 0; i < x.length; i++) {
y = x[i] % 2;
if (y == 1) {
return x[i];
} else {
return 0;
}
}
return x[i];
}
public static int firstOddCount(int x[]) {
int i;
int c = 0;
for (i = 0; i < x.length; i++) {
if (x[i] == odd(x))
c++;
}
return c;
}
}
I'm trying to find the first occurrence of an odd number in the array that has been provided. What is wrong with my program? I can't seem to get the program to count the first odd occurrences.
Your code here:
if (y == 1) {
return x[i];
} else {
return 0;
}
does not work - if a tested number is even, you immediately return 0. Instead you want to skip these even numbers and wait until an odd number comes up. In the end, if you don't find any odd number, you return 0. Here is the corrected version of odd():
int i;
int y;
for (i = 0; i < x.length; i++) {
y = x[i] % 2;
if (y == 1) {
return x[i];
}
}
return 0;
Andr's solution fixes your issue; odd(x) will return 0 if x[0] is even, and x[0] if it is odd.
You could also improve firstOddCount like so: odd(x) will always return the same value, so only calculate it once.
public static int firstOddCount(int x[]) {
int firstOdd = odd(x);
int c=0;
for(int i=0; i < x.length; i++) {
if (x[i]==firstOdd)
c++;
}
return c;
}
Your particular problem is that you return 0 if you find an even number. That means that the list {2, 4, 6, 8, 1} will give you 0, rather than 1, as the first odd number.
What you should do is ignore leading even numbers and continue to process the list.
However, the way you've organised your program, you're processing the first all-even part of the list twice, once in odd() to find the first odd number, then again in firstOddCount() to count how many of that number there are - that's totally unnecessary.
Once you find the first odd number, I think you can be reasonably certain that number (or any other odd number for that matter) does not exist in the space you've already searched. Otherwise it would have been the first odd number. Hence it makes little sense to go back and look at that initial part of the list again.
A way in which you can easily just process the list once is as follows:
public static int firstOddCount (int numbers[]) {
// Find first odd number or end of list.
int idx = 0, len = numbers.length;
while ((idx < len) && ((numbers[idx] % 2) == 0)
idx++;
// If at end of list, everything is even => count(first(odd)) is 0.
if (idx == len)
return 0;
// Otherwise, start counting from current position.
int count = 1, oddnum = numbers[idx];
while (++idx < len)
if (numbers[idx] == oddnum)
count++;
return count;
}
If you are trying to get one element from group you should use 'break' when your condition matched first time else it will give all...

Categories

Resources