Checking if two int arrays have duplicate elements, and extract one of the duplicate elements from them

Using Java's streams could make this quite simpler:

public int[] union(int[] array1, int[] array2) {
    return Stream.of(array1, array2).flatMapToInt(Arrays::stream).distinct().toArray();
}

It will be much easier to do it with Collection API or Stream API. However, you have mentioned that you want to do it purely using arrays and without importing any class, it will require a few lengthy (although simple) processing units. The most important theories that drive the logic is how (given below) a union is calculated:

n(A U B) = n(A) + n(B) - n(A ∩ B)

and

n(Only A) = n(A) - n(A ∩ B)
n(Only B) = n(B) - n(A ∩ B)

A high-level summary of this solution is depicted with the following diagram:

enter image description here

Rest of the logic has been very clearly mentioned through comments in the code itself.

public class Main {
    public static void main(String[] args) {
        // Test
        display(union(new int[] { 1, 2, 3, 4 }, new int[] { 3, 4, 5, 6 }));
        display(union(new int[] { 1, 2, 3 }, new int[] { 4, 5, 6 }));
        display(union(new int[] { 1, 2, 3, 4 }, new int[] { 1, 2, 3, 4 }));
        display(union(new int[] { 1, 2, 3, 4 }, new int[] { 3, 4 }));
        display(union(new int[] { 1, 2, 3, 4 }, new int[] { 4, 5 }));
        display(union(new int[] { 1, 2, 3, 4, 5, 6 }, new int[] { 7, 8 }));
    }

    public static int[] union(int[] array1, int[] array2) {
        // Create an array of the length equal to that of the smaller of the two array
        // parameters
        int[] intersection = new int[array1.length <= array2.length ? array1.length : array2.length];
        int count = 0;

        // Put the duplicate elements into intersection[]
        for (int i = 0; i < array1.length; i++) {
            for (int j = 0; j < array2.length; j++) {
                if (array1[i] == array2[j]) {
                    intersection[count++] = array1[i];
                }
            }
        }

        // Create int []union of the length as per the n(A U B) = n(A) + n(B) - n(A ∩ B)
        int[] union = new int[array1.length + array2.length - count];

        // Copy array1[] minus intersection[] into union[]
        int lastIndex = copySourceOnly(array1, intersection, union, count, 0);

        // Copy array2[] minus intersection[] into union[]
        lastIndex = copySourceOnly(array2, intersection, union, count, lastIndex);

        // Copy intersection[] into union[]
        for (int i = 0; i < count; i++) {
            union[lastIndex + i] = intersection[i];
        }

        return union;
    }

    static int copySourceOnly(int[] source, int[] exclude, int[] target, int count, int startWith) {
        int j, lastIndex = startWith;
        for (int i = 0; i < source.length; i++) {
            // Check if source[i] is present in intersection[]
            for (j = 0; j < count; j++) {
                if (source[i] == exclude[j]) {
                    break;
                }
            }

            // If j has reached count, it means `break;` was not executed i.e. source[i] is
            // not present in intersection[]
            if (j == count) {
                target[lastIndex++] = source[i];

            }
        }
        return lastIndex;
    }

    static void display(int arr[]) {
        System.out.print("[");
        for (int i = 0; i < arr.length; i++) {
            System.out.print(i < arr.length - 1 ? arr[i] + ", " : arr[i]);
        }
        System.out.println("]");
    }
}

Output:

[1, 2, 5, 6, 3, 4]
[1, 2, 3, 4, 5, 6]
[1, 2, 3, 4]
[1, 2, 3, 4]
[1, 2, 3, 5, 4]
[1, 2, 3, 4, 5, 6, 7, 8]

Even with all the restrictions of only using arrays, you can simplify your code a lot. No need to check for sets. Just :

  1. allocate an array to store all elements of the union (i.e., int[] tmp_union ), which at worst will be all elements from both arrays array1 and array2.

  2. iterate over the elements of array1 and compared them against the elements from tmp_union array, add them into the tmp_union array only if they were not yet added to that array.

  3. Repeat 2) for the array2.

During this process keep track of the number of elements added to the tmp_union array so far (i.e., added_so_far). In the end, copy the elements from the tmp_union array into a new array (i.e., unionArray) with space allocated just for the union elements. The code would look something like:

public static int[] union(int[] array1, int[] array2){
    int[] tmp_union = new int[array1.length + array2.length];
    int added_so_far = add_unique(array1, tmp_union, 0);
        added_so_far = add_unique(array2, tmp_union, added_so_far);
    return copyArray(tmp_union, added_so_far);
}

private static int[] copyArray(int[] ori, int size) {
    int[] dest = new int[size];
    for(int i = 0; i < size; i++)
        dest[i] = ori[i];
    return dest;
}

private static int add_unique(int[] array, int[] union, int added_so_far) {
    for (int element : array)
        if (!is_present(union, added_so_far, element))
            union[added_so_far++] = element;
    return added_so_far;
}

private static boolean is_present(int[] union, int added_so_far, int element) {
    for (int z = 0; z < added_so_far; z++)
         if (element == union[z])
             return true;
    return false;
}