Lazy
Lazy

Reputation: 1462

how to compare the Java Byte[] array?

public class ByteArr {

    public static void main(String[] args){
        Byte[] a = {(byte)0x03, (byte)0x00, (byte)0x00, (byte)0x00};
        Byte[] b = {(byte)0x03, (byte)0x00, (byte)0x00, (byte)0x00};
        byte[] aa = {(byte)0x03, (byte)0x00, (byte)0x00, (byte)0x00};
        byte[] bb = {(byte)0x03, (byte)0x00, (byte)0x00, (byte)0x00};

        System.out.println(a);
        System.out.println(b);
        System.out.println(a == b);
        System.out.println(a.equals(b));

        System.out.println(aa);
        System.out.println(bb);
        System.out.println(aa == bb);
        System.out.println(aa.equals(bb));
    }
}

I do not know why all of them print false.

When I run "java ByteArray", the answer is "false false false false".

I think the a[] equals b[] but the JVM is telling me I am wrong, why??

Upvotes: 127

Views: 163226

Answers (16)

Supun Wijerathne
Supun Wijerathne

Reputation: 12958

As a newer solution, you can use

import org.junit.jupiter.api.Assertions.*

assertArrayEquals(aa,bb);

Upvotes: 0

wener
wener

Reputation: 7770

Arrays.equals is not enough for a comparator, you can not check the map contain the data. I copy the code from Arrays.equals, modified to build a Comparator.

class ByteArrays{
    public static <T> SortedMap<byte[], T> newByteArrayMap() {
        return new TreeMap<>(new ByteArrayComparator());
    }

    public static SortedSet<byte[]> newByteArraySet() {
        return new TreeSet<>(new ByteArrayComparator());
    }

    static class ByteArrayComparator implements Comparator<byte[]> {
        @Override
        public int compare(byte[] a, byte[] b) {
            if (a == b) {
                return 0;
            }
            if (a == null || b == null) {
                throw new NullPointerException();
            }

            int length = a.length;
            int cmp;
            if ((cmp = Integer.compare(length, b.length)) != 0) {
                return cmp;
            }

            for (int i = 0; i < length; i++) {
                if ((cmp = Byte.compare(a[i], b[i])) != 0) {
                    return cmp;
                }
            }

            return 0;
        }
    }
}

Upvotes: 0

RoutesMaps.com
RoutesMaps.com

Reputation: 1689

You can also use org.apache.commons.lang.ArrayUtils.isEquals()

Upvotes: 0

Michael Borgwardt
Michael Borgwardt

Reputation: 346536

Because neither == nor the equals() method of the array compare the contents; both only evaluate object identity (== always does, and equals() is not overwritten, so the version from Object is being used).

For comparing the contents, use Arrays.equals().

Upvotes: 1

Rakesh Chaudhari
Rakesh Chaudhari

Reputation: 3510

Java byte compare,

public static boolean equals(byte[] a, byte[] a2) {
        if (a == a2)
            return true;
        if (a == null || a2 == null)
            return false;

        int length = a.length;
        if (a2.length != length)
            return false;

        for (int i = 0; i < length; i++)
            if (a[i] != a2[i])
                return false;

        return true;
    }

Upvotes: 0

Daniil Iaitskov
Daniil Iaitskov

Reputation: 6099

I looked for an array wrapper which makes it comparable to use with guava TreeRangeMap. The class doesn't accept comparator.

After some research I realized that ByteBuffer from JDK has this feature and it doesn't copy original array which is good. More over you can compare faster with ByteBuffer::asLongBuffer 8 bytes at time (also doesn't copy). By default ByteBuffer::wrap(byte[]) use BigEndian so order relation is the same as comparing individual bytes.

.

Upvotes: 0

Jack47
Jack47

Reputation: 194

why a[] doesn't equals b[]? Because equals function really called on Byte[] or byte[] is Object.equals(Object obj). This functions only compares object identify , don't compare the contents of the array.

Upvotes: 0

nagyatka
nagyatka

Reputation: 1

There's a faster way to do that:

Arrays.hashCode(arr1) == Arrays.hashCode(arr2)

Upvotes: -5

Bhavesh Shah
Bhavesh Shah

Reputation: 3389

Try for this:

boolean blnResult = Arrays.equals(byteArray1, byteArray2);

I am also not sure about this, but try this may be it works.

Upvotes: 1

Andrejs
Andrejs

Reputation: 27735

You can also use a ByteArrayComparator from Apache Directory. In addition to equals it lets you compare if one array is greater than the other.

Upvotes: 0

Hovercraft Full Of Eels
Hovercraft Full Of Eels

Reputation: 285460

If you're trying to use the array as a generic HashMap key, that's not going to work. Consider creating a custom wrapper object that holds the array, and whose equals(...) and hashcode(...) method returns the results from the java.util.Arrays methods. For example...

import java.util.Arrays;

public class MyByteArray {
   private byte[] data;

   // ... constructors, getters methods, setter methods, etc...


   @Override
   public int hashCode() {
      return Arrays.hashCode(data);
   }

   @Override
   public boolean equals(Object obj) {
      if (this == obj)
         return true;
      if (obj == null)
         return false;
      if (getClass() != obj.getClass())
         return false;
      MyByteArray other = (MyByteArray) obj;
      if (!Arrays.equals(data, other.data))
         return false;
      return true;
   }


}

Objects of this wrapper class will work fine as a key for your HashMap<MyByteArray, OtherType> and will allow for clean use of equals(...) and hashCode(...) methods.

Upvotes: 1

Dan Vinton
Dan Vinton

Reputation: 26769

have you looked at Arrays.equals()?

Edit: if, as per your comment, the issue is using a byte array as a HashMap key then see this question.

Upvotes: 1

Peter Lawrey
Peter Lawrey

Reputation: 533880

As byte[] is mutable it is treated as only being .equals() if its the same object.

If you want to compare the contents you have to use Arrays.equals(a, b)

BTW: Its not the way I would design it. ;)

Upvotes: 7

mikera
mikera

Reputation: 106401

They are returning false because you are testing for object identity rather than value equality. This returns false because your arrays are actually different objects in memory.

If you want to test for value equality should use the handy comparison functions in java.util.Arrays

e.g.

import java.util.Arrays;

'''''

Arrays.equals(a,b);

Upvotes: 0

soulcheck
soulcheck

Reputation: 36777

Cause they're not equal, ie: they're different arrays with equal elements inside.

Try using Arrays.equals() or Arrays.deepEquals().

Upvotes: 10

Lukasz
Lukasz

Reputation: 7662

Use Arrays.equals() if you want to compare the actual content of arrays that contain primitive types values (like byte).

System.out.println(Arrays.equals(aa, bb));

Use Arrays.deepEquals for comparison of arrays that contain objects.

Upvotes: 246

Related Questions