2017-05-20 16 views
0

質問は、KotlinのイテレータのようなPythonを作成する方法です。このpythonイテレータに相当するkotlinイディオムは何ですか

部分文字列に文字列を解析し、このPythonコードを考えてみましょう:

def parse(strng, idx=1): 
    lst = [] 
    for i, c in itermarks(strng, idx): 
     if c == '}': 
      lst.append(strng[idx:i-1]) 
      break 
     elif c == '{': 
      sublst, idx = parse(strng, i+1) 
      lst.append(sublst) 
     else: 
      lst.append(strng[idx:i-1]) 
      idx = i+1 
    return lst, i 

>>>res,resl = parse('{ a=50 , b=75 , { e=70, f=80 } }') 
>>>print(resl) 
>>>[' a=50', ' b=75', [' e=7', ' f=80'], '', ' f=80'] 

これは単にPythonのイテレータを説明するためにプレー例です:

def findany(strng, idx, chars): 
    """ to emulate 'findany' in kotlin """ 
    while idx < len(strng) and strng[idx] not in chars: 
     idx += 1 
    return idx 

def itermarks(strng, idx=0): 
    while True: 
     idx = findany(strng, idx, ',{}"') 
     if idx >= len(strng): 
      break 
     yield idx, strng[idx] 
     if strng[idx] == '}': 
      break 
     idx += 1 

Kotlinはイテレータと発電機を持っている、と私は理解してタイプごとに1つしか存在できません。私の考えは、ジェネレータと型を持つ型を定義することです。 ((I、C)IterMarks中(STRNG){ ...... }

ため

をしかし、私はどのように行う:だから '解析' からのループのために(上記)、このようになります。

答えて

0

Kotlinは、Iterable<T>(JDKから)とSequence<T>という2つのインターフェイスを使用しますが、最初のものは熱心で、2番目のものは慣例により遅延しています。

イテレータまたはシーケンスを操作するには、th oseインタフェース。 Kotlin stdlibには助けになるヘルパー関数がたくさんあります。

特に、yieldでシーケンスを作成するための2つの関数が1.1に追加されました。それらとその他の機能はgeneratorsと呼ばれます。好きな場合はそれらを使用するか、手動でインターフェイスを実装してください。

+0

また、初期値+次の値を計算するラムダを持つgenerateSequenceもあります。 'null 'を返すとすぐに、' Sequence'が終了します。 –

0

OKには、いくつかの仕事の後、ここではイテレータのためKotlinです:

import kotlin.coroutines.experimental.* 

fun iterMarks(strng: String, idx:Int=0)=buildSequence{ 
    val specials = listOf("\"", "{", "}", ",") 
    var found:Pair<Int,String>? 
    var index = idx 
    while (true){ 
     found = strng.findAnyOf(specials, index) 
     if (found == null) break 
     yield (found) 
     index= found.first + 1 
    } 
} 

主な発見は、イテレータは任意の関数によって返されることができたので、反復子メソッドを追加する必要はありません既存のオブジェクトに追加します。 JetBrains docoは実用的ですが、例がありませんので、上記の例が役立つことを願っています。基本から作業することもできますが、やはり音符はいいですが例はありません。興味があれば、私は他のアプローチについてもっと詳しく説明します。

「解析」のこのコードは、その後動作します:

fun parse(strng:String, idxIn:Int=1): Pair<Any,Int> { 
    var lst:MutableList<Any> = mutableListOf() 
    var idx = idxIn 
    [email protected] for (mark in iterMarks(strng, idx)){ 
     if(mark==null ||mark.first <= idx){ 
      // nothing needed 
     } 
     else 
     { 
      when(mark.second) { 
       "}" -> { 
        lst.add(strng.slice(idx..mark.first - 1)) 
        idx = mark.first + 1 
        [email protected] 
       } 
       "{" -> { 
        val res: Pair<Any, Int> 
        res = parse(strng, mark.first + 1) 
        lst.add(res.first) 
        idx = res.second 
       } 

       "," -> { 
        lst.add(strng.slice(idx..mark.first - 1)) 
        idx = mark.first + 1 
       } 
      } 

     } 
    } 
    return Pair(lst, idx) 

} 

うまくいけば、この例では、イテレータの実装例を提供することで、それKotlinへの新しい隣の人のための少ない作業になります。具体的には、Pythonでイテレータを作成する方法が分かっている場合、この例は便利です。

関連する問題