I have two arrays:
list1 = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
list2 = [2, 4, 6, 8, 10]
How is it possible to make the output look like this?
list3 = [1, 3, 5, 7, 9]
list3[i] = list1[i] - list2[i];
Unfortunately this does not work for me because the two arrays are not same length.
import java.util.Arrays;
import java.util.Scanner;
public class Infinity {
public static int[] InitialiseStudents(int[] students) {
for (int i = 0; i<students.length; i++){
students[i] = i+1;
}
return students;
}
public static int[] AssignJobs (int[] NumberStudents) {
int StudCount = NumberStudents.length;
int[] Array = NumberStudents;
//loop for every day(t), starting at the second day
for (int t = 2; t <= StudCount; t++) {
System.out.println("Tag" + t);
int[] copy = new int[5];
for (int i = t-1, j=0; j < 5; i+=t) {
copy[j++] = Array[i];
}
System.out.println("-------------");
System.out.println(Arrays.toString(copy));
System.out.println("_________");
break;
}
return Array;
}
public static void main( String[] args) {
Scanner scan = new Scanner(System.in);
System.out.println("Enter Number of Students: ");
//int n = scan.nextInt();
int n = 10;
int[] students = new int[n];
InitialiseStudents(students);
students = AssignJobs(students);
System.out.println(Arrays.toString(students));
}
}
To make to task VERY clear I just show you everything I have done and the context. This is my homework which I am curently working. The task is...
Initially, a numbering 1, 2, 3, 4, . . . of the students is determined. Then it will be that
every second (start counting with the first student) becomes Garbage officer (these are
the students with the numbers 2, 4, 6, 8, . . . ), from the rest (students 1, 3,
5, 7, . . . ) every third person becomes a refrigerator representative (these are students 5, 11, 17,
23, . . . ), of the rest (students 1, 3, 7, 9, . . . ) every fourth . . . , from which then
we can think of something for each k-th and from the rest for
every (k+1)-th etc. Apparently, some of the residents (students 1, 3, 7)
omitted during distribution and do not have to complete any of the tasks that arise.
Numbers of these students are called Omitted Numbers.
Program an application OmittedNumbers that exactly the Omitted Numbers
an area 1; : : : ;N retrieves and prints, where N is passed on the command line
will. Only use methods that are iterative.
Solution # 1
Convert your arrays to list
List<Integer> list1 = Arrays.asList(array1);
List<Integer> list2 = Arrays.asList(array2);
For List, you can use removeAll function
list1.removeAll(list2);
System.out.println(list1)
Solution # 2
Traverse through each index and remove items if same as follow
int[] array1 = new int[]{1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
int[] array2 = new int[]{2, 4, 6, 8, 10};
List<Integer> result = new ArrayList<>();
for (int i = 0; i < array1.length; i++) {
for (int j = 0; j < array2.length; j++) {
if (array1[i] == array2[j]) {
result.add(array1[i]);
}
}
}
// convert list to array (if needed)
Integer[] resultArray = result.toArray(new Integer[0]);
Here's a simple implementation:
import java.util.ArrayList;
import java.util.List;
record ChoiceResult(List<Integer> chosen, List<Integer> remainder) {}
public class Choose {
static ChoiceResult choose(int interval, List<Integer> candidates) {
List<Integer> chosen = new ArrayList<>();
List<Integer> remainder = new ArrayList<>();
for (int i = 0; i < candidates.size(); i++) {
if ((i+1) % interval == 0) {
chosen.add(candidates.get(i));
} else {
remainder.add(candidates.get(i));
}
}
return new ChoiceResult(chosen, remainder);
}
public static void main(String[] args) {
List<Integer> students = List.of(1,2,3,4,5,6,7,8,9,10);
ChoiceResult garbage = choose(2, students);
ChoiceResult fridge = choose(3, garbage.remainder());
System.out.println("Garbage: " + garbage.chosen());
System.out.println("Fridge: " + fridge.chosen());
}
}
It has the feature of working with an immutable List for the input to the function.
You can use double-layer for loop filtering,The following is just a sample code, you need to think about the details(For example, how to improve the efficiency of calculation, because the efficiency of double-layer for loop is very low).
public static void main(String[] args) {
int[] arr1 = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
int[] arr2 = {2, 4, 6, 8, 10};
List<Integer> rt = new ArrayList<>();
for (int i = 0; i < arr1.length; i++) {
boolean flag = false;
for (int j = 0; j < arr2.length; j++) {
if(arr1[i] == arr2[j]) {
flag = true;
break;
}
}
if (flag == false) {
rt.add(arr1[i]);
}
}
System.out.println(rt);
Integer[] finalArr = rt.toArray(new Integer[rt.size()]);
for (int i = 0; i < finalArr.length; i++) {
System.out.println(finalArr[i]);
}
}
Collection framework supports union/intersection at base level and just utilize it.
import java.util.ArrayList;
import java.util.List;
public class Test {
public static void main(String[] args) {
List<Integer> list1 = new ArrayList<>(List.of(1, 2, 3, 4, 5, 6, 7, 8, 9, 10));
List<Integer> list2 = new ArrayList<>(List.of(2, 4, 6, 8, 10));
list1.removeAll(list2);
System.out.println(list1);
}
}
Using Stream API:
import java.util.List;
import java.util.stream.Collectors;
public class StreamTest {
public static void main(String[] args) {
List<Integer> list1 = List.of(1, 2, 3, 4, 5, 6, 7, 8, 9, 10);
List<Integer> list2 = List.of(2, 4, 6, 8, 10);
List<Integer> list3 = list1.stream()
.filter(i -> !list2.contains(i))
.collect(Collectors.toList());
System.out.println(list3);
}
}
collection methods reference
Related
How would I change the size of a 2d array without rearranging the numbers in an array mainly using for loops and only built in methods?
For example, {{4,5,6,7,10}, {8,4,3,9,13}} to become {{4}, {5,6}, {7,10,8}, {4,3,9,13}}.
I tried making the 2d array into two separate parts then adding it back to a new 2d array. I'm not sure how I would create the second 2d array.
There are many ways to do this. Here is one that works for any triangular number
of elements that originate in a 2D array.
First, flatten them all into a single array.
int[] oneD = Arrays.stream(src).flatMapToInt(Arrays::stream).toArray();
Then reversing the length which should be k where k = n(n+1)/2 the
number of rows would be the following. And the 2D result is partially allocated.
int rows = (int)(Math.sqrt(2*oneD.length + .25) -.5);
int[][] dest = new int[rows][];
Now it's just a matter of copying from the oneD array to the destination.
for (int i = 0, s = 0, e = 1; i < rows; i++) {
dest[i] = Arrays.copyOfRange(oneD, s, e );
s = e;
e += i+2;
}
for (int[] arr : dest) {
System.out.println(Arrays.toString(arr));
}
Prints
[4]
[5, 6]
[7, 10, 8]
[4, 3, 9, 13]
If I understood your question, I recommend you use List<List<Integer>>, for example ArrayList, insted of pure arrays, and you can set your aggregations like this:
List<List<Integer>> matrix = new ArrayList<>();
List<Integer> values = new ArrayList<>();
// add {4,5,6,7,10} to array, result = {{4,5,6,7,10}}
values = new ArrayList<>(Arrays.asList(4,5,6,7,10));
matrix.add(values);
// add {8,4,3,9,13} to last array, result = {{4,5,6,7,10}, {8,4,3,9,13}}
values = new ArrayList<>(Arrays.asList(8,4,3,9,13));
matrix.add(values);
System.out.println("start="+ matrix);
// reset array or you can use another array to copy
matrix = new ArrayList<>();
values = new ArrayList<>(Arrays.asList(4));
matrix.add(values);
values = new ArrayList<>(Arrays.asList(5,6));
matrix.add(values);
values = new ArrayList<>(Arrays.asList(7,10,8));
matrix.add(values);
values = new ArrayList<>(Arrays.asList(4,3,9,13));
matrix.add(values);
System.out.println("end="+ matrix);
Output:
start=[[4, 5, 6, 7, 10], [8, 4, 3, 9, 13]]
end=[[4], [5, 6], [7, 10, 8], [4, 3, 9, 13]]
A possible not-recommended solution
Flatten the 2d array
Collect with grouping on summation sequence
It might be improved to use single atomic counter (i am unable to think)
import java.util.Arrays;
import java.util.Collection;
import java.util.List;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.stream.Collectors;
public class ArrayResize {
public static void main(String[] args) {
Integer[][] input = new Integer[][] {{10, 11, 12 ,13, 14}, {15, 16, 17, 18, 19}};
AtomicInteger index = new AtomicInteger(0);
AtomicInteger group = new AtomicInteger(1);
Collection<List<Integer>> out = Arrays.stream(input)
.flatMap(i -> Arrays.stream(i)) // flatten
.collect(Collectors.groupingBy(i -> {
final int currentIndex = index.getAndIncrement();
return (group.get() * (group.get() + 1)) / 2 == currentIndex
? group.incrementAndGet() // increment group if index matches the summation of the range
: group.get(); // return the group
}))
.values();
System.out.println(out);
}
}
output has to be any Integer array
import java.util.Arrays;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.stream.Collectors;
public class ArrayResize {
public static void main(String[] args) {
Integer[][] input = new Integer[][] {{10, 11, 12 ,13, 14}, {15, 16, 17, 18, 19}};
AtomicInteger index = new AtomicInteger(0);
AtomicInteger group = new AtomicInteger(1);
Integer[][] output = Arrays.stream(input)
.flatMap(i -> Arrays.stream(i)) // flatten
.collect(Collectors.groupingBy(i -> {
final int currentIndex = index.getAndIncrement();
return (group.get() * (group.get() + 1)) / 2 == currentIndex
? group.incrementAndGet() // increment group if index matches the summation of the range
: group.get(); // return the group
})).values().stream() // stream collection
.map(subgroup -> subgroup.toArray(new Integer[0])) // map subgroups to arrays
.collect(Collectors.toList()) // collect as list of arrays
.toArray(new Integer[0][0]); // convert to array
System.out.println(Arrays.deepToString(output));
}
}
Disclaimer
I would not write the above code in any of my production systems
At the current state, it will fail with parallel stream usage
Solution using index count
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.stream.Collectors;
public class ArrayResize {
public static void main(String[] args) {
Integer[][] input = new Integer[][] {{10, 11, 12 ,13, 14}, {15, 16, 17, 18, 19}};
List<Integer> flattened = Arrays.stream(input).flatMap(i -> Arrays.stream(i)).collect(Collectors.toList());
List<Integer[]> temporary = new ArrayList<>();
final int count = flattened.size();
int start = 0;
int range = 1;
while (start < count) {
temporary.add(flattened.subList(start, Math.min(start + range, count)).toArray(new Integer[0]));
start += range;
range++;
}
Integer[][] result = temporary.toArray(new Integer[0][0]);
System.out.println(Arrays.deepToString(result));
}
}
Here's one way to do it, using pure Java code (e.g. loops) and no methods at all.
static int[][] toTriangle(int[][] input) {
// Count number of values
int valueCount = 0;
for (int[] inputRow : input)
valueCount += inputRow.length;
if (valueCount == 0)
return new int[0][0];
// Determine number of result rows, and how many values that can store
int resultRowCount = 0, resultCount = 0;
for (int row = 0; resultCount < valueCount; row++) {
resultRowCount++;
resultCount += row + 1;
}
int oversize = resultCount - valueCount;
// Build result jagged array (last row is likely truncated)
int[][] result = new int[resultRowCount][];
for (int row = 0; row < resultRowCount - 1; row++)
result[row] = new int[row + 1];
result[resultRowCount - 1] = new int[resultRowCount - oversize];
// Copy values
int inputRow = 0, inputCol = 0;
for (int[] resultRow : result) {
for (int i = 0; i < resultRow.length; i++) {
while (inputCol == input[inputRow].length) {
inputRow++;
inputCol = 0;
}
resultRow[i] = input[inputRow][inputCol++];
}
}
return result;
}
Tests
test(new int[][] {{4,5,6,7,10}, {8,4,3,9,13}});
test(new int[][] {{1,2,3,4}, {}, {5,6,7}});
static void test(int[][] input) {
print("Input", input);
print("Result", toTriangle(input));
}
static void print(String label, int[][] arr) {
System.out.println(label + ":");
for (int[] row : arr) {
System.out.print(" [");
String sep = "";
for (int val : row) {
System.out.print(sep + val);
sep = ", ";
}
System.out.println("]");
}
}
Outputs
Input:
[4, 5, 6, 7, 10]
[8, 4, 3, 9, 13]
Result:
[4]
[5, 6]
[7, 10, 8]
[4, 3, 9, 13]
Input:
[1, 2, 3, 4]
[]
[5, 6, 7]
Result:
[1]
[2, 3]
[4, 5, 6]
[7]
Notice how the last row is truncated in length, since there are not enough values to fill a triangle. The second example also shows that it can handle empty sub-arrays in the input.
So I came across this problem in Java that wants to remove a list of number that has occurred more than twice but keeping the order, and the first two occurrences.
For example, if the list is 2, 3, 5, 4, 5, 2, 4, 3, 5, 2, 4, 4, 2, 10
the expected output would be 2, 3, 5, 4, 5, 2, 4, 3, 10
I've tried several methods, including using a counter int to keep track of the occurrences and filter it out, but I am not sure how I can go about it
class DeDup {
// function to find the element occurring more than 3 times
static void get2Occurrences(int arr[]) {
int i;
int count = 0;
for (i = 0; i < arr.length; i++) {
for (int j = 0; j < arr.length; j++) {
if (arr[i] == arr[j])
count++;
}
if (count < 3 && count > 0) {
//return arr[i];
System.out.print(arr[i] + ", ");
} else {
for (int k = 2; k > 0; k--) {
System.out.print(arr[i] + ", ");
}
}
}
}
// driver code
public static void main(String[]args) {
int arr[] = new int[]{ 2, 3, 5, 4, 5, 2, 4, 3, 5, 2, 4, 4, 2, 10 };
//expected output: 2, 3, 5, 4, 5, 2, 4, 3, 10
//int n = arr.length;
get2Occurrences(arr);
}
}
the expected output would be 2, 3, 5, 4, 5, 2, 4, 3, 10
but i got 2, 2, 3, 3, 5, 5, 4, 4, 5, 5, 2, 2, 4, 4, 3, 3, 5, 5, 2, 2, 4, 4, 4, 4, 2, 2, 10, 10,
I would do it using a pair of Sets: Set.add returns a boolean indicating whether the element was added. Hence:
boolean b = set1.add(num) || set2.add(num);
will be true if it was added into either set - and it will only try to add it to set2 if it was already in set1 - and false otherwise, meaning it was present in both sets already.
Set<Integer> set1 = new HashSet<>();
Set<Integer> set2 = new HashSet<>();
for (Integer a : arr) {
if (set1.add(a) || set2.add(a)) {
System.out.print(a + ", ");
}
}
Ideone demo
Keep track of the number of occurrences found for each element.
Something like this:
static void get2Occurrences(int arr[])
{
// Initialize occurrences found
Hashtable<Integer, Integer> found_elms = new Hashtable<Integer, Integer>();
// Loop over all elements
int counter;
int number;
Integer found;
for (counter = 0; counter < arr.length; counter++)
{
number = arr[counter];
found = found_elms.get(number);
if (found == null)
found = 1;
else
found = found + 1;
found_elms.put(number, found);
if (found < 3)
System.out.print(number + ", ");
}
System.out.println();
} // get2Occurrences
In this solution, you can change the number of repetitions from three to another.
int[] arr = new int[]{2, 3, 5, 4, 5, 2, 4, 3, 5, 2, 4, 4, 2, 10};
Map<Integer, Integer> counting = new HashMap<>();
for (Integer current : arr) {
int count = counting.compute(current, (x, n) -> n == null ? 1 : n + 1);
if (count < 3) {
System.out.print(current + ", ");
}
}
I would propose an insert filter : go through each element with a for loop and insert it into a response array if the response arrays doesnt contain it 2 times yet
import java.util.ArrayList;
import java.util.List;
...
List<Integer> lst = new ArrayList<>();
for (int i : arr) {
if (lst.lastIndexOf(i) == lst.indexOf(i)) {
lst.add(i);
}
}
return lst.stream().mapToInt(i -> i).toArray();
So this is what I came up with in the end
import java.util.ArrayList;
import java.util.Arrays;
class DeDup {
// function to find the element occurring more than 3 times
static void get2Occurrences(ArrayList<Integer> arr)
{
for(int i=0; i<arr.size(); i++){
int count=0;
for(int j=0; j<i; j++){
if(arr.get(j)==arr.get(i)){
count++;
}
}
if (count>=2){
arr.remove(i);
i--;
}
}
System.out.println("Output: "+arr);;
}
// driver code
public static void main(String[] args)
{
ArrayList<Integer> arr = new ArrayList<Integer>(Arrays.asList( 2, 3, 5, 4, 5, 2, 4, 3, 5, 2, 4, 4, 2, 10));
//expected output: 2, 3, 5, 4, 5, 2, 4, 3, 10
//int n = arr.length;
System.out.println("Input: "+arr);
get2Occurrences(arr);
}
}
Solution using Iteartor:
List<Integer> array = Lists.newArrayList(2, 3, 5, 4, 5, 2, 4, 3, 5, 2, 4, 4, 2, 10);
Map<Integer, Integer> control = new HashMap<>();
Iterator<Integer> iterator = array.iterator();
while(iterator.hasNext()) {
Integer element = iterator.next();
Integer occurrences = control.getOrDefault(element, 0);
if (occurrences >= 2) {
iterator.remove();
} else {
control.put(element, occurrences + 1);
}
}
I'm trying to solve a problem on CodeFights called firstDuplicate, that states -
Given an array a that contains only numbers in the range from 1 to
a.length, find the first duplicate number for which the second
occurrence has the minimal index. In other words, if there are more
than 1 duplicated numbers, return the number for which the second
occurrence has a smaller index than the second occurrence of the other
number does. If there are no such elements, return -1.
Example
For a = [2, 3, 3, 1, 5, 2], the output should be firstDuplicate(a) =
3.
There are 2 duplicates: numbers 2 and 3. The second occurrence of 3
has a smaller index than than second occurrence of 2 does, so the
answer is 3.
For a = [2, 4, 3, 5, 1], the output should be firstDuplicate(a) = -1.
My solution -
public class FirstDuplicate {
private static HashMap<Integer, Integer> counts = new HashMap<>();
private static void findSecondIndexFrom(int[] num, int n, int i) {
// given an array, a starting index and a number, find second occurrence of that number beginning from next index
for(int x = i; x < num.length; x++) {
if(num[x] == n) {
// second occurrence found - place in map and terminate
counts.put(n, x);
return;
}
}
}
private static int firstDuplicate(int[] a) {
// for each element in loop, if it's not already in hashmap
// find it's second occurrence in array and place number and index in map
for(int i = 0; i < a.length; i++) {
if(!counts.containsKey(a[i])) {
findSecondIndexFrom(a, a[i], i+1);
}
}
System.out.println(counts);
// if map is empty - no duplicate elements, return -1
if(counts.size() == 0) {
return -1;
}
// else - get array of values from map, sort it, find lowest value and return corresponding key
ArrayList<Integer> values = new ArrayList<>(counts.values());
Collections.sort(values);
int lowest = values.get(0);
//System.out.println(lowest);
for(Map.Entry<Integer, Integer> entries: counts.entrySet()) {
if(entries.getValue() == lowest) {
return entries.getKey();
}
}
return -1;
}
public static void main(String[] args) {
// int[] a = new int[]{2, 3, 3, 1, 5, 2};
//int[] a = new int[]{2, 4, 3, 5, 1};
//int[] a = new int[]{8, 4, 6, 2, 6, 4, 7, 9, 5, 8};
//int[] a = new int[]{1, 1, 2, 2, 1};
int[] a = new int[]{10, 6, 8, 4, 9, 1, 7, 2, 5, 3};
System.out.println(firstDuplicate(a));
}
}
This solution passes only for about 4 of the 11 test cases on CodeFights. However, I manually executed each one of the test cases in my IDE, and each one produces the right result.
I can't figure out why this won't work in CodeFights. Does it have something to do with the use of the static HashMap?
Edited: Since adding and checking if element is present in Set can be done in one step, code can be simplified to:
public static int findDuplicateWithLowestIndex(int... a){
Set<Integer> set = new HashSet<>();
for(int num : a){
if(!set.add(num)){
return num;
}
}
return -1;
}
You're completly right Patrick.
Use this solution: here duplicateIndex should be very large number.
package sample;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
public class Duplicate {
public static Integer secondIndex(Integer[] arr) {
List<Integer> arrlist = new ArrayList<>(Arrays.asList(arr));
int duplicateIndex = 999;
int ele = 0;
for (int i = 0; i < arrlist.size(); i++) {
int secondIndex = getSecondIndex(arrlist, arrlist.get(i));
if (secondIndex >= 0 && duplicateIndex > secondIndex) {
duplicateIndex = secondIndex;
ele = arrlist.get(i);
}
}
return duplicateIndex == 999 ? -1 : ele;
}
public static int getSecondIndex(List<Integer> arr, int ele) {
List<Integer> var0 = new ArrayList<>(arr);
var0.set(var0.indexOf(ele), -1);
return var0.indexOf(ele);
}
public static void main(String[] str) {
// Integer[] arr = new Integer[] { 2, 3, 3, 1, 5, 2 };
// Integer[] arr = new Integer[] { 2, 4, 3, 5, 1 };
// Integer[] arr = new Integer[] { 8, 4, 6, 2, 6, 4, 7, 9, 5, 8 };
// Integer[] arr = new Integer[]{1, 1, 2, 2, 1};
Integer[] arr = new Integer[] { 10, 6, 8, 4, 9, 1, 7, 2, 5, 3 };
System.out.println(secondIndex(arr));
}
}
Solution in Javascript
function solution(a) {
const duplicates = [];
for (const i of a) {
if (duplicates.includes(i))
return i;
else
duplicates.push(i);
}
return -1;
}
console.log(solution([2, 1, 3, 5, 3, 2])); // 3
console.log(solution([2, 2])); // 2
console.log(solution([2, 4, 3, 5, 1])); // -1
I have problem. I try to do develop
Program ask me for some numbers a few times. I give list of numbers. I try to save them in List>. Numbers can be split by space. Now I have this code :
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
public class TimeSeries {
public static void main(String[] args) {
// TODO Auto-generated method stub
System.out.println("Numbers of rows:");
Scanner in = new Scanner(System.in);
int NumberLines = in.nextInt();
in.nextLine();
String Ciag;
List<List<Integer>> ll = new ArrayList<List<Integer>>();
List<Integer> list = new ArrayList<Integer>();
for (int i = 0; i < NumberLines; i++) {
list.clear();
System.out.println("Add row " +(i+1));
Ciag = in.nextLine();
for (int t=0; t<Ciag.length(); t++) {
if(Character.isWhitespace(Ciag.charAt(t)))
{
}
else
{list.add(Character.getNumericValue(Ciag.charAt(t)));
}
}
System.out.println(list);
ll.add(list);
}
System.out.println(ll);
}
}
But my output is (example) :
Numbers of rows:
3
Add row 1
0 0 0
[0, 0, 0]
Add row 2
1 2 3
[1, 2, 3]
Add row 3
54 6 8
[5, 4, 6, 8]
[[5, 4, 6, 8], [5, 4, 6, 8], [5, 4, 6, 8]]
But I need to have [[0,0, 0], [1, 2, 3], [5, 4, 6, 8]]
The problem is that you add the same list into ll multiple times.
You need to add different lists to get the behavior you want.
For that, you need to create a fresh new list in each iteration of the for loop, instead of clearing and reusing the existing list.
Change these lines:
List<List<Integer>> ll = new ArrayList<List<Integer>>();
List<Integer> list = new ArrayList<Integer>();
for (int i = 0; i < NumberLines; i++) {
list.clear();
To this:
List<List<Integer>> ll = new ArrayList<>();
for (int i = 0; i < NumberLines; i++) {
List<Integer> list = new ArrayList<>();
Suppose you are given unique numbers like
11,2,7,6,17,13,8,9,3,5,12
The result will be group of numbers list containing sub list i.e.,
[2,3]-[5,6,7,8,9]-[11,12,13]-[17]
I took this approach to solve this below:
int[] a = { 11, 2, 7, 6, 13,17, 8, 9, 3, 5, 12 };
Arrays.sort(a);
List<List<Integer>> ListMain = new ArrayList<>();
List<Integer> temp = new ArrayList<>();
for (int i = 0; i < a.length; i++) {
if (a[i + 1] == a[i] + 1) {
temp.add(a[i + 1]);
} else {
ListMain.add(temp);
temp.clear();
}
}
Your overall logic is mostly correct. You have a few problems in your execution, though.
You get an array index out of bounds exception because you call a[i+1] when i = a.length. Change the loop condition to a.length - 1.
You need to use a new inner ArrayList each time, otherwise each array will get wiped out. Change temp.clear(); to temp = new ArrayList<>();.
You need to initialize the new list to the first element, not the empty list. Add temp.add(a[0]); at the beginning and temp.add(a[i+1]) when you've detected you need a new sublist.
You need to add the final list at the end, because your condition won't get called at the end of the loop.
Here's the modified program:
import java.util.ArrayList;
import java.util.List;
import java.util.Arrays;
public class SubList {
public static void main(String... args) {
int[] a = { 11, 2, 7, 6, 13,17, 8, 9, 3, 5, 12 };
Arrays.sort(a);
List<List<Integer>> ListMain = new ArrayList<>();
List<Integer> temp = new ArrayList<>();
temp.add(a[0]);
for (int i = 0; i < a.length - 1; i++) {
if (a[i + 1] == a[i] + 1) {
temp.add(a[i + 1]);
} else {
ListMain.add(temp);
temp = new ArrayList<>();
temp.add(a[i+1]);
}
}
ListMain.add(temp);
System.out.println(ListMain);
}
}
Output:
[[2, 3], [5, 6, 7, 8, 9], [11, 12, 13], [17]]
Thanks Garis M Suero for your suggestion after which i got answer
int[] a = { 11, 2, 7, 6, 13,17, 8, 9, 3, 5, 12 };
Arrays.sort(a);
List<List<Integer>> listMain = new ArrayList<List<Integer>>();
List<Integer> temp = new ArrayList<>();
for (int i = 0; i < a.length; i++) {
if ((i + 1<a.length)&&( a[i] + 1==a[i + 1])) {
temp.add(a[i]);
} else {
temp.add(a[i]);
listMain.add(temp);
temp = new ArrayList<>();
}
}
for (List<Integer> lstI : listMain) {
for (Integer i : lstI) {
System.out.println(i);
}
System.out.println("================");
}