2

I'm trying to create a utility method that will accept two arrays as parameters, merge them together, and return the resulting array. Discarding duplicates.

Ideally, the parameters would accept any array type, such as int[] or string[].

I'm using C# .NET 1.1, and therefore do not have access to Generics or Array.Resize().

Is there a better way to merge two arrays, without knowing their type, but returning an array of the same type?

At this time, the following code returns an array of object[]. I'd like the returned array type to match the parameters.

public static object[] MergeArrays(object[] dest, object[] src)
{
    if (dest.GetType() != src.GetType())
        return null;    // The arrays are of different types

    if (dest.Equals(src))
        return dest;    // Don't merge with self

    // We now know there are two compatible and unique arrays
    int delta = src.Length;

    // Cycle through the passed materials and see if they already exist
    for (int i = 0; i < src.Length; i++)
        // Check to see if this material already exists
        for (int j = 0; j < dest.Length; j++)
            if (src[i] == dest[j])
            {
                // The material already exists, so we'll skip it
                src[i] = null;
                delta--;
                break;
            }

    // If there are still objects to merge, increase the array size
    if (delta > 0)
    {
        object[] = new object[dest.Length + delta];
        int index;

        // Copy the original array
        for (index = 0; index < dest.Length; index++)
            tmp[index] = dest[index];

        // Add the new elements
        for (int i = 0; i < src.Length; i++)
        {
            if (src[i] == null)
                continue;
            tmp[index++] = src[i];
        }
        dest = tmp;
    }
    return dest;
}
0

1 Answer 1

1

I believe that this is all legal .NET 1.1:

public static object[] Merge(object[] first, object[] second) {
    if (first == null) {
        throw new ArgumentNullException("first");
    }
    if (second == null) {
        throw new ArgumentNullException("second");
    }
    Type firstType = first.GetType();
    Type secondType = second.GetType();
    if (firstType != secondType) {
        throw new InvalidOperationException("type mismatch");
    }
    Hashtable table = new Hashtable();
    ArrayList items = new ArrayList();
    NewMethod(first, table, items);
    NewMethod(second, table, items);
    return (object[])items.ToArray(firstType.GetElementType());
}

static void NewMethod(object[] array, Hashtable table, ArrayList items) {
    for (int i = 0; i < array.Length; i++) {
        object item = array[i];
        if (!table.Contains(item)) {
            table.Add(item, 1);
            items.Add(item);
        }
    }
}

I'm too lazy to find a good name for NewMethod so I just let Visual Studio default name it after an extract-to-method procedure.

Usage:

object[] a = new string[10];
object[] b = new string[10];

for(int i = 0; i < 10; i++) {
    a[i] = i.ToString();
    b[i] = (i + 5).ToString();
}

object[] c = Merge(a, b);
Console.WriteLine(c.Length);
Console.WriteLine(c.GetType());
for (int i = 0; i < c.Length; i++) {
    Console.WriteLine(c[i]);
}

Output:

15
System.String[]
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15   

Note that if you want to shove an array two T[] where T : ValueType into Merge you have to box the elements first and type the array as an object[]; this is because there is no conversion from T[] to object[] when T : ValueType. Moreover, because GetType is not virtual, the best that you can get out in this case is an object[], not a T[].

Sign up to request clarification or add additional context in comments.

3 Comments

You're welcome; do you have a better name for NewMethod? I'm still thinking.
I normally would go with MergeCore or MergeInner
I actually went with MergeHelper, but MergeCore or MergeInner might be better. Overall, the solution looks elegant and seems to function well. Thanks again!

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.