简体   繁体   中英

android Reflection on NdefMessage Construction fails

I want to instantiate an NdefMessage using an NdefRecord with Reflection. Below a simple codeSnippet that really SHOULD work, but doesn't:

// getting Ndef Message Class OK
Class<?> ndefMessageClass = Class.forName("android.nfc.NdefMessage"); 

//getting NdefRecord class OK
Class<?> ndefRecordClass = Class.forName("android.nfc.NdefRecord");

//getting ArrayOf NdefRecord
Object[] ndefRecords = (Object[])Array.newInstance(ndefRecordClass, 1)

//filling the new Array
//I'm shure I get an Correct NdefRecord, but dont wanna mess the Code here
ndefRecords[0] = getNdefRecord()

//getting the constructor OK
Constructor<?> const = ndefMessageClass.getConstructor(ndefRecords.class)

//initialization fails here
Object myNdefMessage = const.newInstance(ndefRecords)

//same with this
Object ndefMessage = const.newInstance(Arrays.asList(args).toArray());

I can absolutly NOT think of how this can fail, getting following ErrorMessage:

04-16 15:38:42.113: W/System.err(13360): java.lang.IllegalArgumentException: argument 1 should have type android.nfc.NdefRecord[], got android.nfc.NdefRecord

So I get a Constructor recognized correctly. If I try to get it like this:

 Constructor<?> const = ndefMessageClass.getConstructor(ndefRecords[0].getClass())

I get

04-16 15:44:59.621: W/System.err(14033): java.lang.NoSuchMethodException: [class android.nfc.NdefRecord]

while on Debugging it shows me everythis correct. I can access indices of my Array. WHY the hell java tells me that ndefRecords are of class NdefRecords instead of NdefRecords[]??

You problem is that the newInstance method is diamond function (ie function that takes variable number of parameters):

public T newInstance(Object... initargs)

In java, however you can pass in an array to such function and the elements of the array will be considered as consecutive parameters passed in to the function. Thus you get:

public static void main (String [] args)
{
   double [] a = {1.1, 2.2, 4.4};
   System.out.println(avg(a) == avg(1.1, 2.2, 4.4));
}
static double avg (double ... numbers)
{
   double total = 0;
   for (int i = 0; i < numbers.length; i++)
        total += numbers [i];
   return total / numbers.length;
}

And the two calls to the avg function have exactly the same meaning.

One quick fix for you I can think of is to change your call to newInstance with:

Object myNdefMessage = const.newInstance(new Object[] {ndefRecords});

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM