29

How can I flatten the 2 dimensions array int originalArray[][] to 1 dimension array?

    int a [] = {1,2,6,7,2};
    int b [] = {2,44,55,2};
    int c [] = {2,44,511,33};

    int originalArray [][] = new int[][]{a,b,c};
Eric Duminil
  • 52,989
  • 9
  • 71
  • 124
Jessy
  • 15,321
  • 31
  • 83
  • 100

9 Answers9

46

With Guava, you can use either

int[] all = Ints.concat(originalArray);

or

int[] all = Ints.concat(a, b, c);

Kevin Bourrillion
  • 40,336
  • 12
  • 74
  • 87
42

With Java 8 you can "flatMap" the inner arrays:

int[] flatArray = Arrays.stream(originalArray)
        .flatMapToInt(Arrays::stream)
        .toArray();

or:

int[] flatArray = Stream.of(a, b, c)
        .flatMapToInt(Arrays::stream)
        .toArray();
assylias
  • 321,522
  • 82
  • 660
  • 783
9

A simple for loop will do, it is not difficult, but will depend on the order in which you want to copy the values. For instance (based on the fact that in your example the arrays all have the same length):

int[] newArray = new int[3 * a.length];
int index = 0;
for (int n = 0; n < a.length; n++) {
    newArray[index++] = a[n];
    newArray[index++] = b[n];
    newArray[index++] = c[n];
}

or (different order, a, b, c can be of different lengths):

int[] newArray = new int[a.length + b.length + c.length];
System.arraycopy(a, 0, newArray, 0, a.length);
System.arraycopy(b, 0, newArray, a.length, b.length);
System.arraycopy(c, 0, newArray, a.length + b.length, c.length);
Soenderby
  • 157
  • 1
  • 11
rsp
  • 23,135
  • 6
  • 55
  • 69
  • 1
    The example arrays don't have the same length. a.length == 5, b.length == 4, c.length == 4. – phihag Apr 02 '10 at 21:44
  • 1
    Also might be worth mentioning that the two examples end up with different orderings for the final flattened array, if that matters. In the first example, the arrays are 'weaved', while in the second, they are placed 'end-to-end', if that makes sense – Kevin K Apr 08 '10 at 05:41
  • 1
    @Kevin, I think I did mention that: `different order, a, b, c can be of different lengths` – rsp Apr 08 '10 at 08:59
4
int[] oneDArray = new int[arr.length*arr.length];
    //Flatten 2D array to 1D array...
    int s = 0;
    for(int i = 0; i < arr.length; i ++) 
          for(int j = 0; j < arr.length; j ++){                           
              oneDArray[s] = arr[i][j];
              s++;
          } 
Nolesh
  • 6,848
  • 12
  • 75
  • 112
4

There will be 2 steps:

1) find out total number of elements to create a new vector (1d array)

2) iterate through your 2d array in predefined order and copy its elements to the created vector

int elementsNumber = 0;

for (int i = 0; i < originalArray.length; i++) {
   elementsNumber += originalArray[i].length;
}

int[] newArray = new int[elementsNumber];
int j = 0;
for (int i = 0; i < originalArray.length; i++) {
   System.arrayCopy (originalArray[i], 0, newArray, j, originalArray[i].length);
   j += originalArray[i].length;
}
Roman
  • 64,384
  • 92
  • 238
  • 332
2

Since arrays can't be extended (i.e. you have to declare the size of an error upon initialization), you have to traverse the arrays twice:

int size = 0;
for (int[] ar : originalArray) size += ar.length;
int[] result = new int[size];
int pos = 0;
for (int[] ar : originalArray) {
    System.arraycopy(ar, 0, result, pos, ar.length);
    pos += ar.length;
}
phihag
  • 278,196
  • 72
  • 453
  • 469
  • Wow, I'm quite surprised recursion isn't necessary. – dclowd9901 Apr 02 '10 at 21:33
  • is it possible not to use loop? – Jessy Apr 02 '10 at 21:36
  • @Jessy Well, you could use recursion, but that would it make way messier and slower. – phihag Apr 02 '10 at 21:37
  • I think, I should use arraycopy :-) – Jessy Apr 02 '10 at 21:51
  • Note: though it wasn't specified as a requirement, with this technique, there's no way to return to the original arrays without retaining their lengths. The solution by @rsp is close a technique capable of reversing the process. Just pointing out that the requirements of the flattening will dictate the solution. – nicerobot Apr 02 '10 at 22:02
0

one-liner with IntStream

IntStream.concat(
    IntStream.concat( IntStream.of(originalArray[0]), IntStream.of(originalArray[1]) ),
        IntStream.of(originalArray[2]) ).toArray();

gets: [1, 2, 6, 7, 2, 2, 44, 55, 2, 2, 44, 511, 33]

Kaplan
  • 2,572
  • 13
  • 14
0

below code can merge varied 2D arrays (diff sizes of internal array) into a one dimensional array:

 public static Integer[] merge2DArrays(int[][] twoDArray){
        ArrayList<Integer> list = new ArrayList<>();
        for (int i = 0; i < twoDArray.length; i++) {
            for (int j = 0; j < twoDArray[i].length; j++) {
                list.add(twoDArray[i][j]);
            }
        }
    return list.toArray(new Integer[list.size()]);
    }
Dean Jain
  • 1,959
  • 19
  • 15
-1

Count the total number of elements in originalArray. Create new array of that length. Copy elements one by one into the new array.

I am unfamiliar with any library function to do so.

Thorbjørn Ravn Andersen
  • 73,784
  • 33
  • 194
  • 347