How can I assign the NULL to a float/double variable?

13.7k Views Asked by At

I have a problem using JNI.

jboolean z = (jboolean) NULL; // ok
jbyte    b = (jbyte)    NULL; // ok
jchar    c = (jchar)    NULL; // ok
jshort   s = (jshort)   NULL; // ok
jint     i = (jint)     NULL; // ok
jlong    j = (jlong)    NULL; // ok

jobject  l = (jobjec)   NULL; // ok

jfloat   f = (jlong)     NULL; // NOT OK 
jdouble  d = (jdouble)   NULL; // NOT OK

Compiler complaines

[ERROR] /....c:112:28: error: pointer cannot be cast to type 'jfloat' (aka 'float')
[ERROR]   jfloat result = (jfloat) NULL;
[ERROR]                            ^~~~
[ERROR] /usr/include/sys/_types/_null.h:29:15: note: expanded from macro 'NULL'
[ERROR] #define NULL  __DARWIN_NULL
[ERROR]               ^~~~~~~~~~~~~
[ERROR] /usr/include/sys/_types.h:52:23: note: expanded from macro '__DARWIN_NULL'
[ERROR] #define __DARWIN_NULL ((void *)0)
[ERROR]                       ^~~~~~~~~~~
[ERROR] 1 error generated.

How can I fix this?


I'm writing methods for each of those values.

jboolean doSome() {
    jboolean result = (jboolean) NULL;
    /*
     * at here result may be initialized or remain as NULL
     */
    return result;
}

I intended to write a function combines following three methods.

(*env)->GetObjecClass(JNIEnv *, jobject);
(*env)->GetMethodID(JNIEnv *, jclass, char *, char *);
(*env)->CallBooleanMethodA(JNIEnv *, jclass, jmethodID, jvalue *);

like this.

jboolean CallBooleanMethodAMmMs(JNIEnv * env, jobject obj, char * mname,
                                char * msig, jvalue * args) {
  jboolean result = (jboolean) NULL;
  jclass clazz = (*env)->GetObjectClass(env, obj);
  jmethodID methodID = (*env)->GetMethodID(env, clazz, mname, msig);
  if (methodID != NULL) {
    result = (*env)->CallBooleanMethodA(env, obj, methodID, args);
  }
  (*env)->DeleteLocalRef(env, clazz);
  return result;
}

I thought I can use NULL for the case of any unsuccessful situation such as methodID == NULL.

I think I should use a jobject instead of primitives, right?

3

There are 3 best solutions below

1
On BEST ANSWER

You cannot (and should not) assign a pointer to a normal variable.

I really don't know why it allowed for some other normal data types, as you have mentioned. Compiler should have produced same warning equally for all assignment from pointer to other non-pointer data type

NULL is a void pointer defined in stdio.h, which is used to initialize pointer type variables . Use a simple 0 instead of NULLin case you want to initialize non-pointer variables.

0
On

How can I assign the NULL to a float/double variable?

Use intptr_t/uintptr_t which are integer types that can hold the information of a void *.


This will preserve information needed to make a void * again that compares equally to NULL.

 intptr_t iptr = (intptr_t) NULL;
 void *ptr = (void *) iptr;
 assert(ptr == NULL);

This converts the integer to a double but information (e.g. precision) may be lost. If code attempts to convert back to an intptr_t, then void * and then attempts to compare equally to NULL, it may fail.

 intptr_t iptr = (intptr_t) NULL;
 double fp = (double) iptr;

 intptr_t iptr2 = (intptr_t) fp;
 void *ptr = (void *) iptr2;

 // May not succeed
 assert(ptr == NULL);
0
On

NULL is supposed to be used as a special value for pointers, if you don't have an actual object to point to. This is an alternative to Option Types (that are used in other languages and are generally considered a better solution) and is only available for pointer types (because for other types it's easier to just pick one value as value with that "special meaning").

So NULL is treated the same way as any other pointer. While pointer conversion to integer types still makes some sense in certain special cases (even though it's dangerous because depending on the type you may be truncating the pointer), it definitely wouldn't make any sense to convert it to a floating-point number (they are used for numeric calculations which don't make sense with memory addresses).

What are you trying to achieve anyway? If it's just about initializing those variables to a well-defined initial value, try 0.0f and 0.0 instead of NULL.