18

So I have hundreds of fields in a couple of classes and I'd like to write some methods on them where they automatically println each field and its corresponding value

At the moment I have this:

inner class Version(val profile: Profile) {

    @JvmField val MINOR_VERSION = glGetInteger(GL_MINOR_VERSION)

    fun write(file: File? = null) {
        //file.printWriter().use { out -> out.pri }
        this::class.java.fields.forEach {
            println(it.isAccessible)
            println(it.getInt(it)) }
    }
}

But this is what I get:

false
Exception in thread "main" java.lang.IllegalArgumentException: Can not set final int field uno.caps.Caps$Version.MINOR_VERSION to java.lang.reflect.Field
    at sun.reflect.UnsafeFieldAccessorImpl.throwSetIllegalArgumentException(UnsafeFieldAccessorImpl.java:167)
    at sun.reflect.UnsafeFieldAccessorImpl.throwSetIllegalArgumentException(UnsafeFieldAccessorImpl.java:171)
    at sun.reflect.UnsafeFieldAccessorImpl.ensureObj(UnsafeFieldAccessorImpl.java:58)
    at sun.reflect.UnsafeQualifiedIntegerFieldAccessorImpl.getInt(UnsafeQualifiedIntegerFieldAccessorImpl.java:58)

Any idea?

elect
  • 6,765
  • 10
  • 53
  • 119

2 Answers2

45

Instead of using Java fields and Java reflection code, you can also use Kotlin properties and Kotlin reflection classes:

class Reflector {
    val Foo = 1;

    fun printFields() {
        this::class.memberProperties.forEach {
            if (it.visibility == KVisibility.PUBLIC) {
                println(it.name)
                println(it.getter.call(this))
            }
        }
    }
}
BladeCoder
  • 12,779
  • 3
  • 59
  • 51
1

It seems that you are passing the Field variable it as a parameter getInt whereas the parameter should be the object the field belongs to this:

From the Javadoc for Field.getInt(Object obj):

obj - the object to extract the int value from

Perhaps this is what you meant to do:

class Reflector {
    @JvmField val Foo = 1;

    fun printFields() {
        this.javaClass.fields.forEach {
            println(it.isAccessible)
            println(it.getInt(this))
        }
    }
}

fun main(args : Array<String>) {
    Reflector().printFields()
}
Frank Wilson
  • 3,192
  • 1
  • 20
  • 29