Domanda

Vorrei convertire la seguente stringa in un array, array nidificato:

str = "[[this, is],[a, nested],[array]]"

newarray = # this is what I need help with!

newarray.inspect  # => [['this','is'],['a','nested'],['array']]
È stato utile?

Soluzione

Si otterrà ciò che si desidera con YAML.

Ma c'è un piccolo problema con la tua stringa.YAML si aspetta che c'è uno spazio dietro la virgola.Quindi, abbiamo bisogno di questo

str = "[[this, is], [a, nested], [array]]"

Codice:

require 'yaml'
str = "[[this, is],[a, nested],[array]]"
### transform your string in a valid YAML-String
str.gsub!(/(\,)(\S)/, "\\1 \\2")
YAML::load(str)
# => [["this", "is"], ["a", "nested"], ["array"]]

Altri suggerimenti

Per una risata:

 ary = eval("[[this, is],[a, nested],[array]]".gsub(/(\w+?)/, "'\\1'") )
 => [["this", "is"], ["a", "nested"], ["array"]]

Disclaimer:Sicuramente non dovrebbe farlo come eval è una pessima idea, ma è veloce e ha l'utile effetto collaterale di generare un'eccezione se nidificata matrici non sono validi

Si potrebbe anche trattare come quasi-JSON.Se le stringhe sono davvero solo le lettere, come nel tuo esempio, quindi, questo lavoro:

JSON.parse(yourarray.gsub(/([a-z]+)/,'"\1"'))

Se si potrebbe avere caratteri arbitrari (tranne [ ] , ), avresti bisogno di un po ' di più:

JSON.parse("[[this, is],[a, nested],[array]]".gsub(/, /,",").gsub(/([^\[\]\,]+)/,'"\1"'))

Sembra una base di analisi di attività.Generalmente l'approccio che si sta andando a voler fare è creare una funzione ricorsiva con il seguente algoritmo generale

base case (input doesn't begin with '[') return the input
recursive case:
    split the input on ',' (you will need to find commas only at this level)
    for each sub string call this method again with the sub string
    return array containing the results from this recursive method

L'unico leggermente parte difficile qui è di spaccare l'ingresso in un unico ','.Si potrebbe scrivere una funzione separata per questo che sarebbe la scansione attraverso la stringa e tenere un conteggio del openbrackets - closedbrakets visto finora.Poi dividere solo sulle virgole quando il conteggio è uguale a zero.

Fare una funzione ricorsiva che prende la stringa e un intero offset, e la "legge" di un array.Che è, restituire un array o di una stringa (che ha letto) e un numero intero offset di puntamento dopo che la matrice.Per esempio:

s = "[[this, is],[a, nested],[array]]"

yourFunc(s, 1) # returns ['this', 'is'] and 11.
yourFunc(s, 2) # returns 'this' and 6.

Poi si può chiamare con un'altra funzione che fornisce un offset di 0, e fa in modo che la finitura offset è la lunghezza della stringa.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top