Refactor Value.
This commit is contained in:
parent
e317b67a48
commit
7c4d69ec1b
@ -4,6 +4,7 @@
|
||||
### Added
|
||||
- Yaml meta format based on yaml.kt
|
||||
- `Path` builders
|
||||
- Special ValueType for lists
|
||||
|
||||
### Changed
|
||||
- `ListValue` and `DoubleArrayValue` implement `Iterable`.
|
||||
@ -11,6 +12,7 @@
|
||||
- `Meta{}` builder made inline
|
||||
- Moved `Envelope` builder to a top level function. Companion invoke is deprecated.
|
||||
- Context logging moved to the extension
|
||||
- `number` and `string` methods on `Value` moved to extensions (breaking change)
|
||||
|
||||
### Deprecated
|
||||
|
||||
|
@ -84,6 +84,6 @@ public fun <T : Any> Provider.top(target: String, type: KClass<out T>): Map<Name
|
||||
/**
|
||||
* Typed top level content
|
||||
*/
|
||||
public inline fun <reified T : Any> Provider.top(target: String): Map<Name, T> = top(target, T::class)
|
||||
public inline fun <reified T : Any> Provider.top(target: String ): Map<Name, T> = top(target, T::class)
|
||||
|
||||
|
||||
|
@ -17,6 +17,7 @@ public class FrontMatterEnvelopeFormat(
|
||||
) : EnvelopeFormat {
|
||||
|
||||
override fun readPartial(input: Input): PartialEnvelope {
|
||||
@Suppress("VARIABLE_WITH_REDUNDANT_INITIALIZER")
|
||||
var line = ""
|
||||
var offset = 0u
|
||||
do {
|
||||
|
@ -32,57 +32,56 @@ public object BinaryMetaFormat : MetaFormat, MetaFormatFactory {
|
||||
writeUtf8String(str)
|
||||
}
|
||||
|
||||
public fun Output.writeValue(value: Value) {
|
||||
if (value.isList()) {
|
||||
public fun Output.writeValue(value: Value): Unit = when (value.type) {
|
||||
ValueType.NUMBER -> when (value.value) {
|
||||
is Short -> {
|
||||
writeChar('s')
|
||||
writeShort(value.short)
|
||||
}
|
||||
is Int -> {
|
||||
writeChar('i')
|
||||
writeInt(value.int)
|
||||
}
|
||||
is Long -> {
|
||||
writeChar('l')
|
||||
writeLong(value.long)
|
||||
}
|
||||
is Float -> {
|
||||
writeChar('f')
|
||||
writeFloat(value.float)
|
||||
}
|
||||
else -> {
|
||||
writeChar('d')
|
||||
writeDouble(value.double)
|
||||
}
|
||||
}
|
||||
ValueType.STRING -> {
|
||||
writeChar('S')
|
||||
writeString(value.string)
|
||||
}
|
||||
ValueType.BOOLEAN -> {
|
||||
if (value.boolean) {
|
||||
writeChar('+')
|
||||
} else {
|
||||
writeChar('-')
|
||||
}
|
||||
}
|
||||
ValueType.NULL -> {
|
||||
writeChar('N')
|
||||
}
|
||||
ValueType.LIST -> {
|
||||
writeChar('L')
|
||||
writeInt(value.list.size)
|
||||
value.list.forEach {
|
||||
writeValue(it)
|
||||
}
|
||||
} else when (value.type) {
|
||||
ValueType.NUMBER -> when (value.value) {
|
||||
is Short -> {
|
||||
writeChar('s')
|
||||
writeShort(value.number.toShort())
|
||||
}
|
||||
is Int -> {
|
||||
writeChar('i')
|
||||
writeInt(value.number.toInt())
|
||||
}
|
||||
is Long -> {
|
||||
writeChar('l')
|
||||
writeLong(value.number.toLong())
|
||||
}
|
||||
is Float -> {
|
||||
writeChar('f')
|
||||
writeFloat(value.number.toFloat())
|
||||
}
|
||||
else -> {
|
||||
writeChar('d')
|
||||
writeDouble(value.number.toDouble())
|
||||
}
|
||||
}
|
||||
ValueType.STRING -> {
|
||||
writeChar('S')
|
||||
writeString(value.string)
|
||||
}
|
||||
ValueType.BOOLEAN -> {
|
||||
if (value.boolean) {
|
||||
writeChar('+')
|
||||
} else {
|
||||
writeChar('-')
|
||||
}
|
||||
}
|
||||
ValueType.NULL -> {
|
||||
writeChar('N')
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun writeMeta(
|
||||
output: kotlinx.io.Output,
|
||||
meta: hep.dataforge.meta.Meta,
|
||||
descriptor: hep.dataforge.meta.descriptors.NodeDescriptor?
|
||||
descriptor: hep.dataforge.meta.descriptors.NodeDescriptor?,
|
||||
) {
|
||||
output.writeChar('M')
|
||||
output.writeInt(meta.items.size)
|
||||
|
@ -29,9 +29,7 @@ public interface Envelope {
|
||||
/**
|
||||
* Build a static envelope using provided builder
|
||||
*/
|
||||
@Deprecated("Use top level function instead",
|
||||
replaceWith = ReplaceWith("Envelope(block)", "hep.dataforge.io.Envelope")
|
||||
)
|
||||
@Deprecated("Use top level function instead")
|
||||
public inline operator fun invoke(block: EnvelopeBuilder.() -> Unit): Envelope =
|
||||
EnvelopeBuilder().apply(block).seal()
|
||||
}
|
||||
|
@ -7,7 +7,7 @@ import kotlin.test.assertEquals
|
||||
|
||||
|
||||
class EnvelopeFormatTest {
|
||||
val envelope = Envelope.invoke {
|
||||
val envelope = Envelope {
|
||||
type = "test.format"
|
||||
meta{
|
||||
"d" put 22.2
|
||||
|
@ -2,6 +2,7 @@ package hep.dataforge.io
|
||||
|
||||
import hep.dataforge.meta.*
|
||||
import hep.dataforge.meta.JsonMeta.Companion.JSON_ARRAY_KEY
|
||||
import hep.dataforge.values.number
|
||||
import kotlinx.io.asBinary
|
||||
import kotlinx.serialization.json.*
|
||||
import kotlin.test.Test
|
||||
|
@ -817,9 +817,6 @@ public final class hep/dataforge/values/DoubleArrayValue : hep/dataforge/values/
|
||||
public fun <init> ([D)V
|
||||
public fun equals (Ljava/lang/Object;)Z
|
||||
public fun getList ()Ljava/util/List;
|
||||
public fun getNumber ()Ljava/lang/Double;
|
||||
public synthetic fun getNumber ()Ljava/lang/Number;
|
||||
public fun getString ()Ljava/lang/String;
|
||||
public fun getType ()Lhep/dataforge/values/ValueType;
|
||||
public synthetic fun getValue ()Ljava/lang/Object;
|
||||
public fun getValue ()[D
|
||||
@ -832,8 +829,6 @@ public final class hep/dataforge/values/EnumValue : hep/dataforge/values/Value {
|
||||
public fun <init> (Ljava/lang/Enum;)V
|
||||
public fun equals (Ljava/lang/Object;)Z
|
||||
public fun getList ()Ljava/util/List;
|
||||
public fun getNumber ()Ljava/lang/Number;
|
||||
public fun getString ()Ljava/lang/String;
|
||||
public fun getType ()Lhep/dataforge/values/ValueType;
|
||||
public fun getValue ()Ljava/lang/Enum;
|
||||
public synthetic fun getValue ()Ljava/lang/Object;
|
||||
@ -850,8 +845,6 @@ public final class hep/dataforge/values/False : hep/dataforge/values/Value {
|
||||
public static final field INSTANCE Lhep/dataforge/values/False;
|
||||
public fun equals (Ljava/lang/Object;)Z
|
||||
public fun getList ()Ljava/util/List;
|
||||
public fun getNumber ()Ljava/lang/Number;
|
||||
public fun getString ()Ljava/lang/String;
|
||||
public fun getType ()Lhep/dataforge/values/ValueType;
|
||||
public fun getValue ()Ljava/lang/Object;
|
||||
public fun hashCode ()I
|
||||
@ -862,8 +855,7 @@ public final class hep/dataforge/values/LazyParsedValue : hep/dataforge/values/V
|
||||
public fun <init> (Ljava/lang/String;)V
|
||||
public fun equals (Ljava/lang/Object;)Z
|
||||
public fun getList ()Ljava/util/List;
|
||||
public fun getNumber ()Ljava/lang/Number;
|
||||
public fun getString ()Ljava/lang/String;
|
||||
public final fun getString ()Ljava/lang/String;
|
||||
public fun getType ()Lhep/dataforge/values/ValueType;
|
||||
public fun getValue ()Ljava/lang/Object;
|
||||
public fun hashCode ()I
|
||||
@ -874,8 +866,6 @@ public final class hep/dataforge/values/ListValue : hep/dataforge/values/Value,
|
||||
public fun <init> (Ljava/util/List;)V
|
||||
public fun equals (Ljava/lang/Object;)Z
|
||||
public fun getList ()Ljava/util/List;
|
||||
public fun getNumber ()Ljava/lang/Number;
|
||||
public fun getString ()Ljava/lang/String;
|
||||
public fun getType ()Lhep/dataforge/values/ValueType;
|
||||
public synthetic fun getValue ()Ljava/lang/Object;
|
||||
public fun getValue ()Ljava/util/List;
|
||||
@ -888,8 +878,6 @@ public final class hep/dataforge/values/Null : hep/dataforge/values/Value {
|
||||
public static final field INSTANCE Lhep/dataforge/values/Null;
|
||||
public fun equals (Ljava/lang/Object;)Z
|
||||
public fun getList ()Ljava/util/List;
|
||||
public fun getNumber ()Ljava/lang/Number;
|
||||
public fun getString ()Ljava/lang/String;
|
||||
public fun getType ()Lhep/dataforge/values/ValueType;
|
||||
public fun getValue ()Ljava/lang/Object;
|
||||
public fun hashCode ()I
|
||||
@ -900,8 +888,7 @@ public final class hep/dataforge/values/NumberValue : hep/dataforge/values/Value
|
||||
public fun <init> (Ljava/lang/Number;)V
|
||||
public fun equals (Ljava/lang/Object;)Z
|
||||
public fun getList ()Ljava/util/List;
|
||||
public fun getNumber ()Ljava/lang/Number;
|
||||
public fun getString ()Ljava/lang/String;
|
||||
public final fun getNumber ()Ljava/lang/Number;
|
||||
public fun getType ()Lhep/dataforge/values/ValueType;
|
||||
public fun getValue ()Ljava/lang/Object;
|
||||
public fun hashCode ()I
|
||||
@ -912,8 +899,7 @@ public final class hep/dataforge/values/StringValue : hep/dataforge/values/Value
|
||||
public fun <init> (Ljava/lang/String;)V
|
||||
public fun equals (Ljava/lang/Object;)Z
|
||||
public fun getList ()Ljava/util/List;
|
||||
public fun getNumber ()Ljava/lang/Number;
|
||||
public fun getString ()Ljava/lang/String;
|
||||
public final fun getString ()Ljava/lang/String;
|
||||
public fun getType ()Lhep/dataforge/values/ValueType;
|
||||
public fun getValue ()Ljava/lang/Object;
|
||||
public fun hashCode ()I
|
||||
@ -924,8 +910,6 @@ public final class hep/dataforge/values/True : hep/dataforge/values/Value {
|
||||
public static final field INSTANCE Lhep/dataforge/values/True;
|
||||
public fun equals (Ljava/lang/Object;)Z
|
||||
public fun getList ()Ljava/util/List;
|
||||
public fun getNumber ()Ljava/lang/Number;
|
||||
public fun getString ()Ljava/lang/String;
|
||||
public fun getType ()Lhep/dataforge/values/ValueType;
|
||||
public fun getValue ()Ljava/lang/Object;
|
||||
public fun hashCode ()I
|
||||
@ -934,18 +918,16 @@ public final class hep/dataforge/values/True : hep/dataforge/values/Value {
|
||||
|
||||
public abstract interface class hep/dataforge/values/Value {
|
||||
public static final field Companion Lhep/dataforge/values/Value$Companion;
|
||||
public static final field TARGET Ljava/lang/String;
|
||||
public static final field TYPE Ljava/lang/String;
|
||||
public abstract fun equals (Ljava/lang/Object;)Z
|
||||
public abstract fun getList ()Ljava/util/List;
|
||||
public abstract fun getNumber ()Ljava/lang/Number;
|
||||
public abstract fun getString ()Ljava/lang/String;
|
||||
public abstract fun getType ()Lhep/dataforge/values/ValueType;
|
||||
public abstract fun getValue ()Ljava/lang/Object;
|
||||
public abstract fun hashCode ()I
|
||||
}
|
||||
|
||||
public final class hep/dataforge/values/Value$Companion {
|
||||
public static final field TARGET Ljava/lang/String;
|
||||
public static final field TYPE Ljava/lang/String;
|
||||
public final fun of (Ljava/lang/Object;)Lhep/dataforge/values/Value;
|
||||
}
|
||||
|
||||
@ -978,6 +960,9 @@ public final class hep/dataforge/values/ValueKt {
|
||||
public static final fun asValue ([I)Lhep/dataforge/values/Value;
|
||||
public static final fun asValue ([J)Lhep/dataforge/values/Value;
|
||||
public static final fun asValue ([S)Lhep/dataforge/values/Value;
|
||||
public static final fun getNumber (Lhep/dataforge/values/Value;)Ljava/lang/Number;
|
||||
public static final fun getNumberOrNull (Lhep/dataforge/values/Value;)Ljava/lang/Number;
|
||||
public static final fun getString (Lhep/dataforge/values/Value;)Ljava/lang/String;
|
||||
public static final fun parseValue (Ljava/lang/String;)Lhep/dataforge/values/Value;
|
||||
}
|
||||
|
||||
@ -993,6 +978,7 @@ public final class hep/dataforge/values/ValueSerializer : kotlinx/serialization/
|
||||
public final class hep/dataforge/values/ValueType : java/lang/Enum {
|
||||
public static final field BOOLEAN Lhep/dataforge/values/ValueType;
|
||||
public static final field Companion Lhep/dataforge/values/ValueType$Companion;
|
||||
public static final field LIST Lhep/dataforge/values/ValueType;
|
||||
public static final field NULL Lhep/dataforge/values/ValueType;
|
||||
public static final field NUMBER Lhep/dataforge/values/ValueType;
|
||||
public static final field STRING Lhep/dataforge/values/ValueType;
|
||||
|
@ -16,20 +16,16 @@ import kotlinx.serialization.json.*
|
||||
/**
|
||||
* @param descriptor reserved for custom serialization in future
|
||||
*/
|
||||
public fun Value.toJson(descriptor: ValueDescriptor? = null): JsonElement {
|
||||
return if (isList()) {
|
||||
JsonArray(list.map { it.toJson() })
|
||||
} else {
|
||||
when (type) {
|
||||
ValueType.NUMBER -> JsonPrimitive(number)
|
||||
ValueType.STRING -> JsonPrimitive(string)
|
||||
ValueType.BOOLEAN -> JsonPrimitive(boolean)
|
||||
ValueType.NULL -> JsonNull
|
||||
}
|
||||
}
|
||||
public fun Value.toJson(descriptor: ValueDescriptor? = null): JsonElement = when (type) {
|
||||
ValueType.NUMBER -> JsonPrimitive(numberOrNull)
|
||||
ValueType.STRING -> JsonPrimitive(string)
|
||||
ValueType.BOOLEAN -> JsonPrimitive(boolean)
|
||||
ValueType.LIST -> JsonArray(list.map { it.toJson() })
|
||||
ValueType.NULL -> JsonNull
|
||||
}
|
||||
|
||||
//Use these methods to customize JSON key mapping
|
||||
@Suppress("NULLABLE_EXTENSION_OPERATOR_WITH_SAFE_CALL_RECEIVER")
|
||||
private fun String.toJsonKey(descriptor: ItemDescriptor?) = descriptor?.attributes["jsonName"].string ?: toString()
|
||||
|
||||
//private fun NodeDescriptor?.getDescriptor(key: String) = this?.items?.get(key)
|
||||
|
@ -4,10 +4,7 @@ import hep.dataforge.meta.Meta.Companion.VALUE_KEY
|
||||
import hep.dataforge.meta.MetaItem.NodeItem
|
||||
import hep.dataforge.meta.MetaItem.ValueItem
|
||||
import hep.dataforge.names.*
|
||||
import hep.dataforge.values.EnumValue
|
||||
import hep.dataforge.values.Null
|
||||
import hep.dataforge.values.Value
|
||||
import hep.dataforge.values.boolean
|
||||
import hep.dataforge.values.*
|
||||
import kotlinx.serialization.Serializable
|
||||
import kotlinx.serialization.json.Json
|
||||
|
||||
@ -245,7 +242,7 @@ public val MetaItem<*>?.value: Value?
|
||||
|
||||
public val MetaItem<*>?.string: String? get() = value?.string
|
||||
public val MetaItem<*>?.boolean: Boolean? get() = value?.boolean
|
||||
public val MetaItem<*>?.number: Number? get() = value?.number
|
||||
public val MetaItem<*>?.number: Number? get() = value?.numberOrNull
|
||||
public val MetaItem<*>?.double: Double? get() = number?.toDouble()
|
||||
public val MetaItem<*>?.float: Float? get() = number?.toFloat()
|
||||
public val MetaItem<*>?.int: Int? get() = number?.toInt()
|
||||
|
@ -3,10 +3,7 @@ package hep.dataforge.meta
|
||||
import hep.dataforge.meta.transformations.MetaConverter
|
||||
import hep.dataforge.names.Name
|
||||
import hep.dataforge.names.asName
|
||||
import hep.dataforge.values.DoubleArrayValue
|
||||
import hep.dataforge.values.Value
|
||||
import hep.dataforge.values.asValue
|
||||
import hep.dataforge.values.doubleArray
|
||||
import hep.dataforge.values.*
|
||||
import kotlin.properties.ReadWriteProperty
|
||||
import kotlin.reflect.KProperty
|
||||
|
||||
@ -72,7 +69,6 @@ public fun <R> MutableItemDelegate.convert(
|
||||
}
|
||||
|
||||
|
||||
|
||||
/* Read-write delegates for [MutableItemProvider] */
|
||||
|
||||
/**
|
||||
@ -171,7 +167,7 @@ public fun MutableItemProvider.numberList(
|
||||
vararg default: Number,
|
||||
key: Name? = null,
|
||||
): ReadWriteProperty<Any?, List<Number>> = item(key).convert(
|
||||
reader = { it?.value?.list?.map { value -> value.number } ?: listOf(*default) },
|
||||
reader = { it?.value?.list?.map { value -> value.numberOrNull ?: Double.NaN } ?: listOf(*default) },
|
||||
writer = { it.map { num -> num.asValue() }.asValue().asMetaItem() }
|
||||
)
|
||||
|
||||
|
@ -11,7 +11,7 @@ import kotlinx.serialization.Serializable
|
||||
*/
|
||||
@Serializable
|
||||
public enum class ValueType {
|
||||
NUMBER, STRING, BOOLEAN, NULL
|
||||
NUMBER, STRING, BOOLEAN, LIST, NULL
|
||||
}
|
||||
|
||||
/**
|
||||
@ -31,16 +31,6 @@ public interface Value {
|
||||
*/
|
||||
public val type: ValueType
|
||||
|
||||
/**
|
||||
* get this value represented as Number
|
||||
*/
|
||||
public val number: Number
|
||||
|
||||
/**
|
||||
* get this value represented as String
|
||||
*/
|
||||
public val string: String
|
||||
|
||||
/**
|
||||
* get this value represented as List
|
||||
*/
|
||||
@ -51,7 +41,7 @@ public interface Value {
|
||||
override fun hashCode(): Int
|
||||
|
||||
public companion object {
|
||||
public const val TARGET: String = "value"
|
||||
public const val TYPE: String = "value"
|
||||
|
||||
/**
|
||||
* Convert object to value
|
||||
@ -86,16 +76,27 @@ public interface Value {
|
||||
}
|
||||
}
|
||||
|
||||
public val Value.string: String get() = toString()
|
||||
|
||||
/**
|
||||
* get this value represented as Number
|
||||
*/
|
||||
public val Value.numberOrNull: Number?
|
||||
get() = if (this is NumberValue) number else string.toDoubleOrNull()
|
||||
|
||||
/**
|
||||
* Return [Value] number content or throw error if value is not a number
|
||||
*/
|
||||
public val Value.number: Number
|
||||
get() = (if (this is NumberValue) number else numberOrNull ?: error("The value is not a number"))
|
||||
|
||||
/**
|
||||
* A singleton null value
|
||||
*/
|
||||
public object Null : Value {
|
||||
override val value: Any? get() = null
|
||||
override val type: ValueType get() = ValueType.NULL
|
||||
override val number: Number get() = Double.NaN
|
||||
override val string: String get() = "@null"
|
||||
|
||||
override fun toString(): String = value.toString()
|
||||
override fun toString(): String = "@null"
|
||||
|
||||
override fun equals(other: Any?): Boolean = other === Null
|
||||
override fun hashCode(): Int = 0
|
||||
@ -107,9 +108,6 @@ public object Null : Value {
|
||||
public object True : Value {
|
||||
override val value: Any get() = true
|
||||
override val type: ValueType get() = ValueType.BOOLEAN
|
||||
override val number: Number get() = 1.0
|
||||
override val string: String get() = "true"
|
||||
|
||||
override fun toString(): String = value.toString()
|
||||
|
||||
override fun equals(other: Any?): Boolean = other === True
|
||||
@ -122,42 +120,40 @@ public object True : Value {
|
||||
public object False : Value {
|
||||
override val value: Any get() = false
|
||||
override val type: ValueType get() = ValueType.BOOLEAN
|
||||
override val number: Number get() = -1.0
|
||||
override val string: String get() = "false"
|
||||
|
||||
override fun toString(): String = value.toString()
|
||||
|
||||
override fun equals(other: Any?): Boolean = other === False
|
||||
override fun hashCode(): Int = -1
|
||||
}
|
||||
|
||||
public class NumberValue(override val number: Number) : Value {
|
||||
public class NumberValue(public val number: Number) : Value {
|
||||
override val value: Any get() = number
|
||||
override val type: ValueType get() = ValueType.NUMBER
|
||||
override val string: String get() = number.toString()
|
||||
|
||||
override fun toString(): String = number.toString()
|
||||
|
||||
override fun equals(other: Any?): Boolean {
|
||||
if (other !is Value) return false
|
||||
return when (number) {
|
||||
is Short -> number.toShort() == other.number.toShort()
|
||||
is Long -> number.toLong() == other.number.toLong()
|
||||
is Byte -> number.toByte() == other.number.toByte()
|
||||
is Int -> number.toInt() == other.number.toInt()
|
||||
is Float -> number.toFloat() == other.number.toFloat()
|
||||
is Double -> number.toDouble() == other.number.toDouble()
|
||||
else -> number.toString() == other.number.toString()
|
||||
|
||||
val otherNumber = other.numberOrNull ?: return false
|
||||
|
||||
return when (numberOrNull) {
|
||||
is Short -> number.toShort() == otherNumber.toShort()
|
||||
is Long -> number.toLong() == otherNumber.toLong()
|
||||
is Byte -> number.toByte() == otherNumber.toByte()
|
||||
is Int -> number.toInt() == otherNumber.toInt()
|
||||
is Float -> number.toFloat() == otherNumber.toFloat()
|
||||
is Double -> number.toDouble() == otherNumber.toDouble()
|
||||
else -> number.toString() == otherNumber.toString()
|
||||
}
|
||||
}
|
||||
|
||||
override fun hashCode(): Int = number.hashCode()
|
||||
|
||||
override fun toString(): String = value.toString()
|
||||
override fun hashCode(): Int = numberOrNull.hashCode()
|
||||
}
|
||||
|
||||
public class StringValue(override val string: String) : Value {
|
||||
public class StringValue(public val string: String) : Value {
|
||||
override val value: Any get() = string
|
||||
override val type: ValueType get() = ValueType.STRING
|
||||
override val number: Number get() = string.toDouble()
|
||||
|
||||
override fun equals(other: Any?): Boolean {
|
||||
return this.string == (other as? Value)?.string
|
||||
@ -165,21 +161,19 @@ public class StringValue(override val string: String) : Value {
|
||||
|
||||
override fun hashCode(): Int = string.hashCode()
|
||||
|
||||
override fun toString(): String = "\"${value.toString()}\""
|
||||
override fun toString(): String = string
|
||||
}
|
||||
|
||||
public class EnumValue<E : Enum<*>>(override val value: E) : Value {
|
||||
override val type: ValueType get() = ValueType.STRING
|
||||
override val number: Number get() = value.ordinal
|
||||
override val string: String get() = value.name
|
||||
|
||||
override fun toString(): String = value.toString()
|
||||
|
||||
override fun equals(other: Any?): Boolean {
|
||||
return string == (other as? Value)?.string
|
||||
}
|
||||
|
||||
override fun hashCode(): Int = value.hashCode()
|
||||
|
||||
override fun toString(): String = value.toString()
|
||||
}
|
||||
|
||||
public class ListValue(override val list: List<Value>) : Value, Iterable<Value> {
|
||||
@ -188,9 +182,7 @@ public class ListValue(override val list: List<Value>) : Value, Iterable<Value>
|
||||
}
|
||||
|
||||
override val value: List<Value> get() = list
|
||||
override val type: ValueType get() = list.first().type
|
||||
override val number: Number get() = list.first().number
|
||||
override val string: String get() = list.first().string
|
||||
override val type: ValueType get() = ValueType.LIST
|
||||
|
||||
override fun toString(): String = list.joinToString(prefix = "[", postfix = "]")
|
||||
|
||||
@ -200,7 +192,7 @@ public class ListValue(override val list: List<Value>) : Value, Iterable<Value>
|
||||
if (this === other) return true
|
||||
if (other !is Value) return false
|
||||
if (other is DoubleArrayValue) {
|
||||
return DoubleArray(list.size) { list[it].number.toDouble() }.contentEquals(other.value)
|
||||
return DoubleArray(list.size) { list[it].numberOrNull?.toDouble() ?: Double.NaN }.contentEquals(other.value)
|
||||
}
|
||||
return list == other.list
|
||||
}
|
||||
@ -208,8 +200,6 @@ public class ListValue(override val list: List<Value>) : Value, Iterable<Value>
|
||||
override fun hashCode(): Int {
|
||||
return list.hashCode()
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
public fun Number.asValue(): Value = NumberValue(this)
|
||||
|
@ -24,6 +24,7 @@ public object ValueSerializer : KSerializer<Value> {
|
||||
ValueType.NUMBER -> decodeDouble().asValue() //TODO differentiate?
|
||||
ValueType.BOOLEAN -> decodeBoolean().asValue()
|
||||
ValueType.STRING -> decodeString().asValue()
|
||||
ValueType.LIST -> decodeSerializableValue(ListSerializer(ValueSerializer)).asValue()
|
||||
}
|
||||
}
|
||||
|
||||
@ -45,6 +46,7 @@ public object ValueSerializer : KSerializer<Value> {
|
||||
ValueType.NUMBER -> encodeDouble(value.double)
|
||||
ValueType.BOOLEAN -> encodeBoolean(value.boolean)
|
||||
ValueType.STRING -> encodeString(value.string)
|
||||
ValueType.LIST -> encodeSerializableValue(ListSerializer(ValueSerializer),value.list)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -4,12 +4,11 @@ package hep.dataforge.values
|
||||
/**
|
||||
* A value built from string which content and type are parsed on-demand
|
||||
*/
|
||||
public class LazyParsedValue(override val string: String) : Value {
|
||||
public class LazyParsedValue(public val string: String) : Value {
|
||||
private val parsedValue by lazy { string.parseValue() }
|
||||
|
||||
override val value: Any? get() = parsedValue.value
|
||||
override val type: ValueType get() = parsedValue.type
|
||||
override val number: Number get() = parsedValue.number
|
||||
|
||||
override fun toString(): String = string
|
||||
|
||||
@ -24,9 +23,7 @@ public fun String.lazyParseValue(): LazyParsedValue = LazyParsedValue(this)
|
||||
* A performance optimized version of list value for doubles
|
||||
*/
|
||||
public class DoubleArrayValue(override val value: DoubleArray) : Value, Iterable<Double> {
|
||||
override val type: ValueType get() = ValueType.NUMBER
|
||||
override val number: Double get() = value.first()
|
||||
override val string: String get() = value.first().toString()
|
||||
override val type: ValueType get() = ValueType.LIST
|
||||
override val list: List<Value> get() = value.map { NumberValue(it) }
|
||||
|
||||
override fun equals(other: Any?): Boolean {
|
||||
|
@ -9,10 +9,9 @@ import hep.dataforge.meta.MetaBuilder
|
||||
public fun Value.isNull(): Boolean = this == Null
|
||||
|
||||
/**
|
||||
* Check if value is list. This method checks the type of the value, not the number of the elements.
|
||||
* So it will return `true` for empty lists and lists of one elements.
|
||||
* Check if value is list.
|
||||
*/
|
||||
public fun Value.isList(): Boolean = this is Iterable<*>
|
||||
public fun Value.isList(): Boolean = this.type == ValueType.LIST
|
||||
|
||||
public val Value.boolean: Boolean
|
||||
get() = this == True
|
||||
|
@ -19,6 +19,7 @@ class DynamicMetaTest {
|
||||
d.ob.booleanNode = true
|
||||
|
||||
val meta = DynamicMeta(d)
|
||||
println(meta)
|
||||
assertEquals(true, meta["ob.booleanNode"].boolean)
|
||||
assertEquals(2, meta["array"].value?.list?.get(1)?.int)
|
||||
assertEquals(4, meta.items.size)
|
||||
|
@ -32,5 +32,6 @@ public val ColumnHeader<Value>.textWidth: Int
|
||||
ValueType.STRING -> 16
|
||||
ValueType.BOOLEAN -> 5
|
||||
ValueType.NULL -> 5
|
||||
ValueType.LIST -> 32
|
||||
null -> 16
|
||||
}
|
||||
|
@ -111,8 +111,8 @@ public class TextTable(
|
||||
private fun Output.writeValue(value: Value, width: Int, left: Boolean = true) {
|
||||
require(width > 5) { "Width could not be less than 5" }
|
||||
val str: String = when (value.type) {
|
||||
ValueType.NUMBER -> value.number.toString() //TODO apply decimal format
|
||||
ValueType.STRING -> value.string.take(width)
|
||||
ValueType.NUMBER -> value.numberOrNull.toString() //TODO apply decimal format
|
||||
ValueType.STRING, ValueType.LIST -> value.string.take(width)
|
||||
ValueType.BOOLEAN -> if (value.boolean) {
|
||||
"true"
|
||||
} else {
|
||||
|
@ -6,6 +6,7 @@ import hep.dataforge.tables.get
|
||||
import hep.dataforge.tables.row
|
||||
import hep.dataforge.values.Value
|
||||
import hep.dataforge.values.int
|
||||
import hep.dataforge.values.string
|
||||
import kotlinx.coroutines.flow.toList
|
||||
import kotlinx.coroutines.runBlocking
|
||||
import kotlinx.io.ExperimentalIoApi
|
||||
|
@ -16,9 +16,7 @@ import java.util.zip.ZipEntry
|
||||
import java.util.zip.ZipOutputStream
|
||||
import kotlin.reflect.KClass
|
||||
|
||||
typealias FileFormatResolver<T> = (Path, Meta) -> IOFormat<T>
|
||||
|
||||
|
||||
public typealias FileFormatResolver<T> = (Path, Meta) -> IOFormat<T>
|
||||
|
||||
private fun newZFS(path: Path): FileSystem {
|
||||
val fsProvider = FileSystemProvider.installedProviders().find { it.scheme == "jar" }
|
||||
@ -84,7 +82,7 @@ public fun <T : Any> DataTreeBuilder<T>.file(
|
||||
* Read the directory as a data node. If [path] is a zip archive, read it as directory
|
||||
*/
|
||||
@DFExperimental
|
||||
fun <T : Any> IOPlugin.readDataDirectory(
|
||||
public fun <T : Any> IOPlugin.readDataDirectory(
|
||||
path: Path,
|
||||
type: KClass<out T>,
|
||||
formatResolver: FileFormatResolver<T>
|
||||
|
Loading…
Reference in New Issue
Block a user