Skip to content

Commit

Permalink
Improve CharCode and Engine.suggest()
Browse files Browse the repository at this point in the history
  • Loading branch information
bingzheung committed Jul 4, 2024
1 parent 01b86cf commit 7e71e51
Show file tree
Hide file tree
Showing 4 changed files with 79 additions and 50 deletions.
52 changes: 52 additions & 0 deletions app/src/main/java/org/jyutping/jyutping/extensions/CharCode.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
package org.jyutping.jyutping.extensions

fun String.charcode(): Int? {
if (this.length >= 10) return null
val codes = this.mapNotNull { it.intercode() }
if (codes.size != this.length) return null
return codes.combined()
}
fun String.shortcutCharcode(): Int? {
if (this.length >= 10) return null
val codes = this.mapNotNull { it.intercode() }
if (codes.size != this.length) return null
val code = codes
.map { if (it == 44) 29 else it } // Replace 'y' with 'j'
.combined()
return code
}

fun Iterable<Int>.combined(): Int {
if (this.count() >= 10) return 0
return this.fold(0) { acc, i -> acc * 100 + i }
}

fun Char.intercode(): Int? = when (this) {
'a' -> 20
'b' -> 21
'c' -> 22
'd' -> 23
'e' -> 24
'f' -> 25
'g' -> 26
'h' -> 27
'i' -> 28
'j' -> 29
'k' -> 30
'l' -> 31
'm' -> 32
'n' -> 33
'o' -> 34
'p' -> 35
'q' -> 36
'r' -> 37
's' -> 38
't' -> 39
'u' -> 40
'v' -> 41
'w' -> 42
'x' -> 43
'y' -> 44
'z' -> 45
else -> null
}
Original file line number Diff line number Diff line change
Expand Up @@ -13,45 +13,3 @@ val String.Companion.space: String

val String.Companion.separator: String
get() = "'"

fun String.charcode(): Int? {
if (this.length >= 10) return null
val codes = this.mapNotNull { it.intercode() }
if (codes.size != this.length) return null
return codes.combined()
}

private fun Iterable<Int>.combined(): Int {
if (this.count() >= 10) return 0
return this.fold(0) { acc, i -> acc * 100 + i }
}

private fun Char.intercode(): Int? = when (this) {
'a' -> 20
'b' -> 21
'c' -> 22
'd' -> 23
'e' -> 24
'f' -> 25
'g' -> 26
'h' -> 27
'i' -> 28
'j' -> 29
'k' -> 30
'l' -> 31
'm' -> 32
'n' -> 33
'o' -> 34
'p' -> 35
'q' -> 36
'r' -> 37
's' -> 38
't' -> 39
'u' -> 40
'v' -> 41
'w' -> 42
'x' -> 43
'y' -> 44
'z' -> 45
else -> null
}
10 changes: 7 additions & 3 deletions app/src/main/java/org/jyutping/jyutping/keyboard/Engine.kt
Original file line number Diff line number Diff line change
Expand Up @@ -6,14 +6,18 @@ import org.jyutping.jyutping.utilities.DatabaseHelper

object Engine {
fun suggest(text: String, segmentation: Segmentation, db: DatabaseHelper): List<Candidate> {
if (db.canProcess(text).not()) return emptyList()
if (segmentation.maxLength() < 1) return processVerbatim(text, db)
return process(text, segmentation, db)
}
private fun processVerbatim(text: String, db: DatabaseHelper): List<Candidate> {
val rounds = text.indices.map { number ->
val rounds: MutableList<List<Candidate>> = mutableListOf()
for (number in text.indices) {
val leading = text.dropLast(number)
return db.match(text = leading, input = leading) + db.shortcut(text = leading)
val round = db.match(text = leading, input = leading) + db.shortcut(text = leading)
rounds.add(round)
}
return rounds.flatten<Candidate>().distinct()
return rounds.flatten().distinct()
}
private fun process(text: String, segmentation: Segmentation, db: DatabaseHelper): List<Candidate> {
val primary = query(text, segmentation, db)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,9 @@ import android.database.sqlite.SQLiteDatabase
import android.database.sqlite.SQLiteOpenHelper
import org.jyutping.jyutping.extensions.charcode
import org.jyutping.jyutping.extensions.convertedS2T
import org.jyutping.jyutping.extensions.intercode
import org.jyutping.jyutping.extensions.isIdeographic
import org.jyutping.jyutping.extensions.shortcutCharcode
import org.jyutping.jyutping.keyboard.Candidate
import org.jyutping.jyutping.keyboard.SegmentToken
import org.jyutping.jyutping.search.CantoneseLexicon
Expand Down Expand Up @@ -334,10 +336,23 @@ class DatabaseHelper(context: Context, databaseName: String) : SQLiteOpenHelper(
return null
}

fun canProcess(text: String): Boolean {
val value = text.firstOrNull()?.intercode() ?: 0
if (value == 0) return false
val code = if (value == 44) 29 else value // Replace 'y' with 'j'
val command = "SELECT rowid FROM lexicontable WHERE shortcut = $code LIMIT 1;"
val cursor = this.readableDatabase.rawQuery(command, null)
if (cursor.moveToFirst()) {
cursor.close()
return true
} else {
return false
}
}
fun shortcut(text: String): List<Candidate> {
val code: Int = text.shortcutCharcode() ?: 0
if (code == 0) return emptyList()
val candidates: MutableList<Candidate> = mutableListOf()
if (text.isBlank()) return candidates
val code: Int = text.charcode() ?: 0
val command = "SELECT rowid, word, romanization FROM lexicontable WHERE shortcut = $code LIMIT 50;"
val cursor = this.readableDatabase.rawQuery(command, null)
while (cursor.moveToNext()) {
Expand All @@ -350,10 +365,10 @@ class DatabaseHelper(context: Context, databaseName: String) : SQLiteOpenHelper(
cursor.close()
return candidates
}
fun match(text: String, input: String, mark: String? = null, limit: Int? = null): List<Candidate> {
val candidates: MutableList<Candidate> = mutableListOf()
if (text.isBlank()) return candidates
fun match(text: String, input: String, mark: String? = null): List<Candidate> {
if (text.isBlank()) return emptyList()
val code: Int = text.hashCode()
val candidates: MutableList<Candidate> = mutableListOf()
val command = "SELECT rowid, word, romanization FROM lexicontable WHERE ping = ${code};"
val cursor = this.readableDatabase.rawQuery(command, null)
while (cursor.moveToNext()) {
Expand Down

0 comments on commit 7e71e51

Please sign in to comment.