https://kotlinlang.org logo
Docs
Join the conversationJoin Slack
Channels
100daysofcode
100daysofkotlin
100daysofkotlin-2021
advent-of-code
aem
ai
alexa
algeria
algolialibraries
amsterdam
android
android-architecture
android-databinding
android-studio
androidgithubprojects
androidthings
androidx
androidx-xprocessing
anime
anko
announcements
apollo-kotlin
appintro
arabic
argentina
arkenv
arksemdevteam
armenia
arrow
arrow-contributors
arrow-meta
ass
atlanta
atm17
atrium
austin
australia
austria
awesome-kotlin
ballast
bangladesh
barcelona
bayarea
bazel
beepiz-libraries
belgium
berlin
big-data
books
boston
brazil
brikk
budapest
build
build-tools
bulgaria
bydgoszcz
cambodia
canada
carrat
carrat-dev
carrat-feed
chicago
chile
china
chucker
cincinnati-user-group
cli
clikt
cloudfoundry
cn
cobalt
code-coverage
codeforces
codemash-precompiler
codereview
codingame
codingconventions
coimbatore
collaborations
colombia
colorado
communities
competitive-programming
competitivecoding
compiler
compose
compose-android
compose-desktop
compose-hiring
compose-ios
compose-mp
compose-ui-showcase
compose-wear
compose-web
connect-audit-events
corda
cork
coroutines
couchbase
coursera
croatia
cryptography
cscenter-course-2016
cucumber-bdd
cyprus
czech
dagger
data2viz
databinding
datascience
dckotlin
debugging
decompose
decouple
denmark
deprecated
detekt
detekt-hint
dev-core
dfw
docs-revamped
dokka
domain-driven-design
doodle
dsl
dublin
dutch
eap
eclipse
ecuador
edinburgh
education
effective-kotlin
effectivekotlin
emacs
embedded-kotlin
estatik
event21-community-content
events
exposed
failgood
fb-internal-demo
feed
firebase
flow
fluid-libraries
forkhandles
forum
fosdem
fp-in-kotlin
framework-elide
freenode
french
fritz2
fuchsia
functional
funktionale
gamedev
ge-kotlin
general-advice
georgia
geospatial
german-lang
getting-started
github-workflows-kt
glance
godot-kotlin
google-io
gradle
graphic
graphkool
graphql
graphql-kotlin
graviton-browser
greece
grpc
gsoc
gui
hackathons
hacktoberfest
hamburg
hamkrest
helios
helsinki
hexagon
hibernate
hikari-cp
hire-me
hiring
hongkong
hoplite
http4k
hungary
hyderabad
image-processing
india
indonesia
inkremental
intellij
intellij-plugins
intellij-tricks
internships
introduce-yourself
io
ios
iran
israel
istanbulcoders
italian
jackson-kotlin
jadx
japanese
jasync-sql
java-to-kotlin-refactoring
javadevelopers
javafx
javalin
javascript
jdbi
jhipster-kotlin
jobsworldwide
jpa
jshdq
juul-libraries
jvm-ir-backend-feedback
jxadapter
k2-early-adopters
kaal
kafka
kakao
kalasim
kapt
karachi
karg
karlsruhe
kash_shell
kaskade
kbuild
kdbc
kgen-doc-tools
kgraphql
kinta
klaxon
klock
kloudformation
kmdc
kmm-español
kmongo
knbt
knote
koalaql
koans
kobalt
kobweb
kodein
kodex
kohesive
koin
koin-dev
komapper
kondor-json
kong
kontent
kontributors
korau
korean
korge
korim
korio
korlibs
korte
kotest
kotest-contributors
kotless
kotlick
kotlin-asia
kotlin-beam
kotlin-by-example
kotlin-csv
kotlin-data-storage
kotlin-foundation
kotlin-fuel
kotlin-in-action
kotlin-inject
kotlin-latam
kotlin-logging
kotlin-multiplatform-contest
kotlin-mumbai
kotlin-native
kotlin-pakistan
kotlin-plugin
kotlin-pune
kotlin-roadmap
kotlin-samples
kotlin-sap
kotlin-serbia
kotlin-spark
kotlin-szeged
kotlin-website
kotlinacademy
kotlinbot
kotlinconf
kotlindl
kotlinforbeginners
kotlingforbeginners
kotlinlondon
kotlinmad
kotlinprogrammers
kotlinsu
kotlintest
kotlintest-devs
kotlintlv
kotlinultimatechallenge
kotlinx-datetime
kotlinx-files
kotlinx-html
kotrix
kotson
kovenant
kprompt
kraph
krawler
kroto-plus
ksp
ktcc
ktfmt
ktlint
ktor
ktp
kubed
kug-leads
kug-torino
kvision
kweb
lambdaworld_cadiz
lanark
language-evolution
language-proposals
latvia
leakcanary
leedskotlinusergroup
lets-have-fun
libgdx
libkgd
library-development
linkeddata
lithuania
london
losangeles
lottie
love
lychee
macedonia
machinelearningbawas
madrid
malaysia
mathematics
meetkotlin
memes
meta
metro-detroit
mexico
miami
micronaut
minnesota
minutest
mirror
mockk
moko
moldova
monsterpuzzle
montreal
moonbean
morocco
motionlayout
mpapt
mu
multiplatform
mumbai
munich
mvikotlin
mvrx
myndocs-oauth2-server
naming
navigation-architecture-component
nepal
new-mexico
new-zealand
newname
nigeria
nodejs
norway
npm-publish
nyc
oceania
ohio-kotlin-users
oldenburg
oolong
opensource
orbit-mvi
osgi
otpisani
package-search
pakistan
panamá
pattern-matching
pbandk
pdx
peru
philippines
phoenix
pinoy
pocketgitclient
polish
popkorn
portugal
practical-functional-programming
proguard
prozis-android-backup
pyhsikal
python
python-contributors
quasar
random
re
react
reaktive
realm
realworldkotlin
reductor
reduks
redux
redux-kotlin
refactoring-to-kotlin
reflect
refreshversions
reports
result
rethink
revolver
rhein-main
rocksdb
romania
room
rpi-pico
rsocket
russian
russian_feed
russian-kotlinasfirst
rx
rxjava
san-diego
science
scotland
scrcast
scrimage
script
scripting
seattle
serialization
server
sg-user-group
singapore
skia-wasm-interop-temp
skrape-it
slovak
snake
sofl-user-group
southafrica
spacemacs
spain
spanish
speaking
spek
spin
splitties
spotify-mobius
spring
spring-security
squarelibraries
stackoverflow
stacks
stayhungrystayfoolish
stdlib
stlouis
strife-discord-lib
strikt
students
stuttgart
sudan
swagger-gradle-codegen
swarm
sweden
swing
swiss-user-group
switzerland
talking-kotlin
tallinn
tampa
teamcity
tegal
tempe
tensorflow
terminal
test
testing
testtestest
texas
tgbotapi
thailand
tornadofx
touchlab-tools
training
tricity-kotlin-user-group
trójmiasto
truth
tunisia
turkey
turkiye
twitter-feed
uae
udacityindia
uk
ukrainian
uniflow
unkonf
uruguay
utah
uuid
vancouver
vankotlin
vertx
videos
vienna
vietnam
vim
vkug
vuejs
web-mpp
webassembly
webrtc
wimix_sentry
wwdc
zircon
Powered by Linen
codereview
  • m

    Mike

    01/16/2019, 12:49 PM
    test(1) results in “12.0” test(2) results in “13.0" Ran in Scratch file of IntelliJ, hence no
    println
    What am I missing? I would have expected the val to require an initial value, and complain if it’s assigned, but it appears not.
    p
    3 replies · 2 participants
  • d

    Dalinar

    01/26/2019, 9:24 AM
    import org.apache.logging.log4j.core.Filter; import org.apache.logging.log4j.core.Layout; import org.apache.logging.log4j.core.LogEvent; import org.apache.logging.log4j.core.appender.AbstractAppender; import org.apache.logging.log4j.core.appender.AppenderLoggingException; import org.apache.logging.log4j.core.config.plugins.Plugin; import org.apache.logging.log4j.core.config.plugins.PluginAttribute; import org.apache.logging.log4j.core.config.plugins.PluginElement; import org.apache.logging.log4j.core.config.plugins.PluginFactory; import org.apache.logging.log4j.core.layout.PatternLayout; import java.io.Serializable; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReadWriteLock; import java.util.concurrent.locks.ReentrantReadWriteLock; /** * <h2>AnsiConsoleAppender</h2> * * <h3>notes</h3> * <li>class name need not match the @Plugin name</li> * <h3>more<h3/> * <li><a href="https://stackoverflow.com/a/24220688/270143">How to Create a Custom Appender in log4j2?</a></li> */ @Plugin(name="AnsiConsoleAppender", category="Core", elementType="appender", printObject=true) public final class AnsiConsoleAppender extends AbstractAppender { private final ReadWriteLock rwLock = new ReentrantReadWriteLock(); private final Lock readLock = rwLock.readLock(); protected AnsiConsoleAppender(String name, Filter filter, Layout<? extends Serializable> layout, final boolean ignoreExceptions) { super(name, filter, layout, ignoreExceptions); } // The append method is where the appender does the work. // Given a log event, you are free to do with it what you want. // This example demonstrates: // 1. Concurrency: this method may be called by multiple threads concurrently // 2. How to use layouts // 3. Error handling //@Override public void append(LogEvent event) { try { final byte[] bytes = getLayout().toByteArray(event); System.out.write("YO: ".getBytes()); System.out.write(bytes); } catch (Exception ex) { if (!ignoreExceptions()) throw new AppenderLoggingException(ex); } } // Your custom appender needs to declare a factory method // annotated with
    @PluginFactory
    . Log4j will parse the configuration // and call this factory method to construct an appender instance with // the configured attributes. @PluginFactory public static AnsiConsoleAppender createAppender( @PluginAttribute("name") String name, @PluginElement("Layout") Layout<? extends Serializable> layout, @PluginElement("Filter") final Filter filter, @PluginAttribute("otherAttribute") String otherAttribute) { if (name == null) { LOGGER.error("No name provided for AnsiConsoleAppenderImpl"); return null; } if (layout == null) { layout = PatternLayout.createDefaultLayout(); } return new AnsiConsoleAppender(name, filter, layout, true); } }
    r
    1 reply · 2 participants
  • u

    ursus

    01/30/2019, 3:17 AM
    Also, the calls are very similar, just they act on different domains (think CRUD account, CRUD message, etc) -- does it even make sense to break it up to AccountCrud-er, etc to keep the interface file shorter?
    d
    a
    +1
    21 replies · 4 participants
  • m

    Marc Knaup

    01/30/2019, 9:12 AM
    What's better (faster? more memory efficient?) when creating mutable maps where the insertion order doesn't matter? Use
    mutableMapOf()
    and
    toMutableMap()
    which use
    LinkedHashMap
    or instead
    hashMapOf()
    and
    HashMap(other)
    ?
    g
    u
    10 replies · 3 participants
  • d

    Dalinar

    02/01/2019, 6:06 AM
    anyone know how to migrate this code from https://github.com/Kotlin/KEEP/blob/master/proposals/coroutines.md ?
    fun <T> future(context: CoroutineContext = CommonPool, block: suspend () -> T): CompletableFuture<T> =
            CompletableFutureCoroutine<T>(context).also { block.startCoroutine(completion = it) }
    
    class CompletableFutureCoroutine<T>(override val context: CoroutineContext) : CompletableFuture<T>(), Continuation<T> {
        override fun resumeWith(result: Result<T>) {
            result
                    .onSuccess { complete(it) }
                    .onFailure { completeExceptionally(it) }
        }
    }
    suspend fun <T> CompletableFuture<T>.await(): T =
            suspendCoroutine { cont: Continuation<T> ->
                whenComplete { result, exception ->
                    if (exception == null) // the future has been completed normally
                        cont.resume(result)
                    else // the future has completed with an exception
                        cont.resumeWithException(exception)
                }
            }
    I mean, is it correct apart from the
    CommonPool
    part? should I just replace
    CommonPool
    with
    EmptyCoroutineContext
    ?
    g
    8 replies · 2 participants
  • u

    ursus

    02/05/2019, 4:35 AM
    Is it worth it to provide "lesser scoped" interface of the same instance, if its be "hacked" via casting?
    interface ReadFooRepository {
    	fun getFoos() : List<Foo>
    }
    
    class FooRepository : ReadFooRepository {
    	override fun getFoos() ...
    	fun saveFoo(foo: Foo) ...
    }
    @provides @singleton fooRepository() : FooRepository = FooRepository()
    @provides readFooRepository(fooRepository: FooRepository) : ReadFooRepository = fooRepository
    class FooViewModel(private val readFooRepository : ReadFooRepository)
     ... only consume values
    h
    2 replies · 2 participants
  • v

    vpriscan

    02/10/2019, 8:00 PM
    is it bad or good practice to use global variables representing "services", like this one:
    val esClient: RestHighLevelClient by lazy {
        createEsClient(
            hosts = arrayOf(HttpHost("localhost", 9200, "http"))
        )
    }
    t
    1 reply · 2 participants
  • p

    pajatopmr

    02/11/2019, 4:47 AM
    Coroutines are incredibly complex, as I have learned over the past week or so. As part of a movie/tv app I am writing, I faced the need to fetch millions of lines of JSON data for a half dozen or so lists. This is my second take at a daily task to update these records in the app. Critique’s much appreciated:
    g
    20 replies · 2 participants
  • m

    mersan

    02/12/2019, 12:40 AM
    -.kt
    d
    2 replies · 2 participants
  • m

    mersan

    02/12/2019, 12:44 AM
    here_is_the_input_if_someone_likes_to_try_it.js
    d
    2 replies · 2 participants
  • r

    rook

    02/15/2019, 3:04 PM
    Just looking for feedback on this Presenter abstract that I’ve recently converted to Kotlin and tweaked. https://gist.github.com/nukeforum/8bc40d330adb9558d2060f08ac87b0e6
    s
    d
    18 replies · 3 participants
  • s

    sitepodmatt

    02/20/2019, 2:47 AM
    use destructing on val comments in line 5 to avoid .first and .second too
    p
    1 reply · 2 participants
  • b

    breandan

    02/21/2019, 3:03 PM
    Any ideas how to solve this type inference issue? I would like to return a generic anonymous function whose type is determined by the outer function, without having to specify the type explicitly at the call site: https://stackoverflow.com/q/54799122/1772342
    a
    3 replies · 2 participants
  • r

    rook

    02/22/2019, 5:19 PM
    Is there a way for me to make
    invoke()
    inlined or otherwise achieve what I’m attempting in
    doWork()
    ?
    -.kt
    m
    2 replies · 2 participants
  • e

    elect

    03/03/2019, 6:53 PM
    Wonder if there is a nice way to make this shorter
    protected fun prepareStandardSemaphores(device: VulkanDevice): ConcurrentHashMap<StandardSemaphores, VkSemaphore_Array> {
            val map = ConcurrentHashMap<StandardSemaphores, VkSemaphore_Array>()
            StandardSemaphores.values().forEach {
                map[it] = VkSemaphore_Array(swapchain.images.size) {
                    vkDev.createSemaphore(semaphoreCreateInfo) 
                }
            }
            return map
        }
    d
    s
    14 replies · 3 participants
  • c

    chansek

    03/04/2019, 7:47 PM
    This looks non scalable to me
    d
    h
    +1
    7 replies · 4 participants
  • a

    arekolek

    03/06/2019, 9:25 AM
    fun foo(bar: List<Int>): Int {
        check(bar.isNotEmpty())
    
        return bar.max()!! / 2
    }
    How would you deal with
    max
    returning a nullable value, other than
    !!
    ? Does it bother you?
    w
    m
    +2
    5 replies · 5 participants
  • s

    sitepodmatt

    03/06/2019, 9:26 AM
    what should happen when max returns a null value?
    d
    1 reply · 2 participants
  • o

    oday

    03/15/2019, 4:51 PM
    how can I catch it while still keeping the method signature and just bouncing back succesfully? I am ok with ignoring this exception
    a
    u
    3 replies · 3 participants
  • t

    tenprint

    03/16/2019, 2:42 PM
    This is probably not ideal… open to any feedback
    sharedElements?.let { thisSharedElements -> 
      names?.let { thisNames ->
        viewHolder?.let { thisViewHolder ->
          thisSharedElements[thisNames[0]] = thisViewHolder.itemView
        }
      }
    }
    p
    u
    8 replies · 3 participants
  • g

    gjesse

    04/08/2019, 3:31 PM
    wonder what people think about this - sometimes i think the elvis operator can be a little confusing, especially in combination with other operators - using an orElse function to specify a default
    fun <T> T?.orElse(default: T) = this ?: default
    for example i have a when statement like this
    return when {
               foo.blah?.someNullableFlag ?: false -> true
    }
    vs
    return when {
               foo.blah?.someNullableFlag.orElse(false) -> true
    }
    s
    e
    +1
    10 replies · 4 participants
  • s

    snowe

    04/09/2019, 8:25 PM
    called like this
    incomeTypes.forEach {
                val incomeType = IncomeType.valueOf(it, IncomeType.UNKNOWN)
    p
    b
    9 replies · 3 participants
  • d

    Dominaezzz

    04/28/2019, 1:32 PM
    Need to return an immutable variable number of items from a function. Should I return a
    List<T>
    or
    Array<T>
    ?
    l
    m
    9 replies · 3 participants
  • e

    elect

    05/13/2019, 8:50 PM
    how may I rewrite this more functional?
    // Request several formats, the first found will be used
                for (request in requestFormats)
                    for (avail in availFormat)
                        if (avail.format == request && avail.colorSpace == requestColorSpace)
                            return avail
                
                // If none of the requested image formats could be found, use the first available
                return availFormat[0]
    l
    2 replies · 2 participants
  • a

    arekolek

    05/14/2019, 12:06 PM
    In this case I’d say you’re right. I’d use a sealed class if some field would be always null for
    PeriodType.Past
    for example, but if everything is the same, enum should be fine
    ➕ 2
    e
    1 reply · 2 participants
  • a

    addamsson

    05/20/2019, 7:42 PM
    I'm not sure this is the right place to ask but I'm struggling a bit with API design. I've posted this on stack exchange as well: https://softwareengineering.stackexchange.com/questions/392156/designing-a-builder-as-a-compile-time-state-machine
    t
    2 replies · 2 participants
  • e

    elect

    05/27/2019, 2:15 PM
    can this be converted to some functional-programming construct?
    int insertionIndex = 0;
                            for (insertionIndex = 0; insertionIndex < activeActionSetsList.Count; insertionIndex++) {
                                if (activeActionSetsList[insertionIndex].nPriority > activeSet.nPriority)
                                    break;
                            }
    d
    2 replies · 2 participants
  • d

    Dominaezzz

    06/06/2019, 7:29 PM
    Anyone know of a collection version of
    Map<K, V>.putIfAbsent(key: K, value: V)
    ?
    putAll
    overrides existing values sadly.
    s
    19 replies · 2 participants
  • e

    elect

    06/13/2019, 8:10 AM
    my first sketch is to have
    DoBlendRoutine
    as a suspend function and
    blendRoutine
    as a
    Job?
    , however I'm not sure about the
    StartCoroutine
    part.. I think I shall directly
    launch { }
    at that point
    d
    1 reply · 2 participants
  • d

    Dominaezzz

    06/15/2019, 4:03 PM
    I want to calculate the length of the longest string of characters in a string that don't contain a
    \n
    .
    val text = "some te\nxt about stuff\nshort"
    text.split('\n').map { it.length }.max() // 14
    Can I do this without creating new string objects and still be functional?
    g
    d
    +1
    4 replies · 4 participants
Powered by Linen
Title
d

Dominaezzz

06/15/2019, 4:03 PM
I want to calculate the length of the longest string of characters in a string that don't contain a
\n
.
val text = "some te\nxt about stuff\nshort"
text.split('\n').map { it.length }.max() // 14
Can I do this without creating new string objects and still be functional?
g

gildor

06/16/2019, 1:45 PM
Just use standard imperative loop and iterate on string chars and increment counter?
d

dumptruckman

06/20/2019, 6:28 PM
Out of curiosity, why?
d

Dominaezzz

06/20/2019, 6:31 PM
I just happen to be converting html tables (jsoup) to markdown for a generated KDoc. Some of the columns entries have
\n
and I need to calculate the width of the column.
u

ursus

06/22/2019, 1:51 AM
maxBy { it.lenght } gives you the longest string
View count: 18