2012-09-05 15 views
7

provo a compilare seguente codice:std.algorithm.joiner (stringa [], stringa) - perché gli elementi di risultato sono dchar e non char?

import std.algorithm; 
void main() 
{ 
    string[] x = ["ab", "cd", "ef"]; // 'string' is same as 'immutable(char)[]' 
    string space = " "; 
    char z = joiner(x, space).front(); // error 
} 

Compilation con dmd si conclude con l'errore:

test.d(8): Error: cannot implicitly convert expression (joiner(x,space).front()) of type dchar to char 

Modifica char z-dchar z fa risolvere il messaggio di errore, ma mi interessa il motivo per cui appare nella primo posto.

Perché il risultato di joiner(string[],string).front() è dchar e non char?

(non c'è niente su questo nella documentazione http://dlang.org/phobos/std_algorithm.html#joiner)

risposta

11

Tutte le stringhe sono trattate come gamme di dchar. Questo perché un dchar è garantito come un singolo punto di codice, poiché in UTF-32, ogni unità di codice è un punto di codice, mentre in UTF-8 (char) e UTF-16 (wchar), il numero di unità di codice per codice il punto varia. Quindi, se stavi operando sui singoli char s o wchar s, dovresti operare su pezzi di caratteri anziché su interi caratteri, il che sarebbe molto brutto. Se non sai molto su unicode, ti consiglio di leggere this article di Joel Spolsky. Spiega le cose abbastanza bene.

In ogni caso, poiché operano su singoli char s e wchar s non ha senso, stringhe di char e wchar sono trattati come intervalli di dchar (ElementType!string è dchar), il che significa che quanto gamme, questi ultimi non hanno length (hasLength!string è false - walkLength deve essere utilizzato per ottenere la loro lunghezza), non sono affettabili (hasSlicing!string è false), e non sono indicizzabili (isRandomAccess!string è false). Ciò significa anche che qualsiasi cosa che costruisca una nuova gamma da qualsiasi tipo di stringa produrrà un intervallo di dchar. joiner è uno di quelli. Ci sono alcune funzioni che capiscono l'unicode e le stringhe di casi speciali per l'efficienza, sfruttando la lunghezza, l'affettatura e l'indicizzazione dove possono, ma a meno che il risultato non sia in definitiva una porzione dell'originale, qualsiasi intervallo restituito dovrà essere reso di dchar s.

Quindi, front su qualsiasi intervallo di caratteri sarà sempre dchar e popFront verrà sempre visualizzato un punto di codice completo.

Se non si conoscono molto le gamme, consiglierei di leggere this. È un capitolo di un libro su D che è online ed è attualmente il miglior tutorial sulle gamme che abbiamo. Dovremmo davvero ottenere un articolo appropriato sugli intervalli (incluso il modo in cui funzionano con le stringhe) su dlang.org, ma nessuno è ancora riuscito a scriverlo. Indipendentemente da ciò, avrete bisogno di avere almeno una conoscenza di base per poter utilizzare molte delle librerie standard di D (in particolare std.algorithm), perché le utilizza molto pesantemente.

Problemi correlati