Remove early maps problems (#408)
This commit is contained in:
@@ -13,9 +13,9 @@ class HashMap<K, V> private constructor(
|
|||||||
override var size: Int = 0
|
override var size: Int = 0
|
||||||
private set
|
private set
|
||||||
|
|
||||||
// private var keysView: HashSet<K>? = null
|
private var keysView: HashSet<K>? = null
|
||||||
// private var valuesView: HashMapValues<V>? = null
|
private var valuesView: HashMapValues<V>? = null
|
||||||
// private var entriesView: HashMapEntrySet<K, V>? = null
|
private var entriesView: HashMapEntrySet<K, V>? = null
|
||||||
|
|
||||||
// ---------------------------- functions ----------------------------
|
// ---------------------------- functions ----------------------------
|
||||||
|
|
||||||
@@ -90,45 +90,30 @@ class HashMap<K, V> private constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
override val keys: MutableSet<K> get() {
|
override val keys: MutableSet<K> get() {
|
||||||
return HashSet(this)
|
val cur = keysView
|
||||||
|
return if (cur == null) {
|
||||||
// Caching creates a reference cycle and thus leads to memory leaks;
|
val new = HashSet(this)
|
||||||
// TODO: fix and enable.
|
keysView = new
|
||||||
|
new
|
||||||
// val cur = keysView
|
} else cur
|
||||||
// return if (cur == null) {
|
|
||||||
// val new = HashSet(this)
|
|
||||||
// keysView = new
|
|
||||||
// new
|
|
||||||
// } else cur
|
|
||||||
}
|
}
|
||||||
|
|
||||||
override val values: MutableCollection<V> get() {
|
override val values: MutableCollection<V> get() {
|
||||||
return HashMapValues(this)
|
val cur = valuesView
|
||||||
|
return if (cur == null) {
|
||||||
// Caching creates a reference cycle and thus leads to memory leaks;
|
val new = HashMapValues(this)
|
||||||
// TODO: fix and enable.
|
valuesView = new
|
||||||
|
new
|
||||||
// val cur = valuesView
|
} else cur
|
||||||
// return if (cur == null) {
|
|
||||||
// val new = HashMapValues(this)
|
|
||||||
// valuesView = new
|
|
||||||
// new
|
|
||||||
// } else cur
|
|
||||||
}
|
}
|
||||||
|
|
||||||
override val entries: MutableSet<MutableMap.MutableEntry<K, V>> get() {
|
override val entries: MutableSet<MutableMap.MutableEntry<K, V>> get() {
|
||||||
return HashMapEntrySet(this)
|
val cur = entriesView
|
||||||
|
return if (cur == null) {
|
||||||
// Caching creates a reference cycle and thus leads to memory leaks;
|
val new = HashMapEntrySet(this)
|
||||||
// TODO: fix and enable.
|
entriesView = new
|
||||||
|
return new
|
||||||
// val cur = entriesView
|
} else cur
|
||||||
// return if (cur == null) {
|
|
||||||
// val new = HashMapEntrySet(this)
|
|
||||||
// entriesView = new
|
|
||||||
// return new
|
|
||||||
// } else cur
|
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun equals(other: Any?): Boolean {
|
override fun equals(other: Any?): Boolean {
|
||||||
@@ -246,7 +231,7 @@ class HashMap<K, V> private constructor(
|
|||||||
private fun findKey(key: K): Int {
|
private fun findKey(key: K): Int {
|
||||||
var hash = hash(key)
|
var hash = hash(key)
|
||||||
var probesLeft = maxProbeDistance
|
var probesLeft = maxProbeDistance
|
||||||
while (true) {
|
while (true) {
|
||||||
val index = hashArray[hash]
|
val index = hashArray[hash]
|
||||||
if (index == 0) return TOMBSTONE
|
if (index == 0) return TOMBSTONE
|
||||||
if (index > 0 && keysArray[index - 1] == key) return index - 1
|
if (index > 0 && keysArray[index - 1] == key) return index - 1
|
||||||
@@ -265,7 +250,7 @@ class HashMap<K, V> private constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
internal fun addKey(key: K): Int {
|
internal fun addKey(key: K): Int {
|
||||||
retry@ while (true) {
|
retry@ while (true) {
|
||||||
var hash = hash(key)
|
var hash = hash(key)
|
||||||
// put is allowed to grow maxProbeDistance with some limits (resize hash on reaching limits)
|
// put is allowed to grow maxProbeDistance with some limits (resize hash on reaching limits)
|
||||||
val tentativeMaxProbeDistance = (maxProbeDistance * 2).coerceAtMost(hashSize / 2)
|
val tentativeMaxProbeDistance = (maxProbeDistance * 2).coerceAtMost(hashSize / 2)
|
||||||
|
|||||||
@@ -417,14 +417,8 @@ public fun <K, V> Iterable<Pair<K, V>>.toMap(): Map<K, V> {
|
|||||||
/**
|
/**
|
||||||
* Populates and returns the [destination] mutable map with key-value pairs from the given collection of pairs.
|
* Populates and returns the [destination] mutable map with key-value pairs from the given collection of pairs.
|
||||||
*/
|
*/
|
||||||
@Fixme
|
public fun <K, V, M : MutableMap<in K, in V>> Iterable<Pair<K, V>>.toMap(destination: M): M
|
||||||
public fun <K, V, M : MutableMap<in K, in V>> Iterable<Pair<K, V>>.toMap(destination: M): M {
|
= destination.apply { putAll(this@toMap) }
|
||||||
for (pair in this) {
|
|
||||||
destination.put(pair.first, pair.second)
|
|
||||||
}
|
|
||||||
return destination
|
|
||||||
}
|
|
||||||
// = destination.apply { putAll(this@toMap) }
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns a new map containing all key-value pairs from the given array of pairs.
|
* Returns a new map containing all key-value pairs from the given array of pairs.
|
||||||
@@ -440,14 +434,8 @@ public fun <K, V> Array<out Pair<K, V>>.toMap(): Map<K, V> = when(size) {
|
|||||||
/**
|
/**
|
||||||
* Populates and returns the [destination] mutable map with key-value pairs from the given array of pairs.
|
* Populates and returns the [destination] mutable map with key-value pairs from the given array of pairs.
|
||||||
*/
|
*/
|
||||||
@Fixme
|
public fun <K, V, M : MutableMap<in K, in V>> Array<out Pair<K, V>>.toMap(destination: M): M
|
||||||
public fun <K, V, M : MutableMap<in K, in V>> Array<out Pair<K, V>>.toMap(destination: M): M {
|
= destination.apply { putAll(this@toMap) }
|
||||||
// = destination.apply { putAll(this@toMap) }
|
|
||||||
for (pair in this) {
|
|
||||||
destination.put(pair.first, pair.second)
|
|
||||||
}
|
|
||||||
return destination
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns a new map containing all key-value pairs from the given sequence of pairs.
|
* Returns a new map containing all key-value pairs from the given sequence of pairs.
|
||||||
@@ -459,14 +447,8 @@ public fun <K, V> Sequence<Pair<K, V>>.toMap(): Map<K, V> = toMap(HashMap<K, V>(
|
|||||||
/**
|
/**
|
||||||
* Populates and returns the [destination] mutable map with key-value pairs from the given sequence of pairs.
|
* Populates and returns the [destination] mutable map with key-value pairs from the given sequence of pairs.
|
||||||
*/
|
*/
|
||||||
@Fixme
|
public fun <K, V, M : MutableMap<in K, in V>> Sequence<Pair<K, V>>.toMap(destination: M): M
|
||||||
public fun <K, V, M : MutableMap<in K, in V>> Sequence<Pair<K, V>>.toMap(destination: M): M {
|
= destination.apply { putAll(this@toMap) }
|
||||||
for (pair in this) {
|
|
||||||
destination.put(pair.first, pair.second)
|
|
||||||
}
|
|
||||||
return destination
|
|
||||||
}
|
|
||||||
// = destination.apply { putAll(this@toMap) }
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns a new read-only map containing all key-value pairs from the original map.
|
* Returns a new read-only map containing all key-value pairs from the original map.
|
||||||
|
|||||||
@@ -3,7 +3,7 @@ import stdio.*
|
|||||||
|
|
||||||
fun parseLine(line: String, separator: Char) : List<String> {
|
fun parseLine(line: String, separator: Char) : List<String> {
|
||||||
val result = mutableListOf<String>()
|
val result = mutableListOf<String>()
|
||||||
var builder = StringBuilder()
|
val builder = StringBuilder()
|
||||||
var quotes = 0
|
var quotes = 0
|
||||||
for (ch in line) {
|
for (ch in line) {
|
||||||
when {
|
when {
|
||||||
@@ -14,7 +14,7 @@ fun parseLine(line: String, separator: Char) : List<String> {
|
|||||||
(ch == '\n') || (ch == '\r') -> {}
|
(ch == '\n') || (ch == '\r') -> {}
|
||||||
(ch == separator) && (quotes % 2 == 0) -> {
|
(ch == separator) && (quotes % 2 == 0) -> {
|
||||||
result.add(builder.toString())
|
result.add(builder.toString())
|
||||||
builder = StringBuilder()
|
builder.length = 0
|
||||||
}
|
}
|
||||||
else -> builder.append(ch)
|
else -> builder.append(ch)
|
||||||
}
|
}
|
||||||
@@ -37,6 +37,8 @@ fun main(args: Array<String>) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
val keyValue = mutableMapOf<String, Int>()
|
||||||
|
|
||||||
try {
|
try {
|
||||||
memScoped {
|
memScoped {
|
||||||
val bufferLength = 64 * 1024
|
val bufferLength = 64 * 1024
|
||||||
@@ -47,10 +49,16 @@ fun main(args: Array<String>) {
|
|||||||
if (nextLine == null || nextLine.isEmpty()) break
|
if (nextLine == null || nextLine.isEmpty()) break
|
||||||
|
|
||||||
val records = parseLine(nextLine, ',')
|
val records = parseLine(nextLine, ',')
|
||||||
println(records[column])
|
val key = records[column]
|
||||||
|
val current = keyValue[key] ?: 0
|
||||||
|
keyValue[key] = current + 1
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} finally {
|
} finally {
|
||||||
fclose(file)
|
fclose(file)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
keyValue.forEach {
|
||||||
|
println("${it.key} -> ${it.value}")
|
||||||
|
}
|
||||||
}
|
}
|
||||||
@@ -10,4 +10,5 @@ To run use
|
|||||||
|
|
||||||
./CsvParser.kexe ./European_Mammals_Red_List_Nov_2009.csv 4 100
|
./CsvParser.kexe ./European_Mammals_Red_List_Nov_2009.csv 4 100
|
||||||
|
|
||||||
It will print fifth column (Family, zero-based index) in first 100 rows of the CSV file.
|
It will print number of all unique entries in fifth column
|
||||||
|
(Family, zero-based index) in first 100 rows of the CSV file.
|
||||||
|
|||||||
Reference in New Issue
Block a user