Kotlin. How to store property in value class?

79 Views Asked by At

I'm trying to create value class for storing money. And I need to store private money format. Here is my code:

@JvmInline
value class Money internal constructor(val rawValue: String) {

    private val format: MoneyFormat = MoneyFormat.WHOLE

And I retrieve error:

Value class cannot have properties with backing fields

But on the other hand, if you look at the implementation of kotlin.time.Duration you can find the property storageUnit there. And as far as I understand, it is necessary to store the current duration unit.

How can I save the format in my class so that I can add methods that can transfer money from one format to another?

1

There are 1 best solutions below

0
On

The whole point of inline/value classes is that internally we don't instantiate an object of the class, but we use its single value directly (at least where it is possible). In your case that means we don't want to pass Money object, but a string directly. We can't store this additional format value in the string object, so we can't add such property.

Duration.storageUnit is different:

private val storageUnit get() = if (isInNanos()) DurationUnit.NANOSECONDS else DurationUnit.MILLISECONDS

It doesn't store any additional data in the object. Whenever we access storageUnit property, it calculates the needed value dynamically and returns it. It doesn't store it anywhere.

Looking at your example, I suppose you wanted to do the same:

private val format: MoneyFormat get() = MoneyFormat.WHOLE

Please note get(). This is different than your original code. Your code creates a field and stores MoneyFormat.WHOLE when instantiating the object. After adding get() no field is created, only the getter and the getter returns MoneyFormat.WHOLE.