2013-04-25 14 views
16

Con Delphi XE4 per la piattaforma iOS è stato introdotto un nuovo tipo di stringa: stringhe a zero immutabili. Finora Delphi aveva copiato su stringhe scrivibili. Quindi la domanda è: cosa significa questo per la mia programmazione futura? Ci sono vantaggi di un tipo di stringa rispetto all'altro? Quali sono le insidie ​​di cui devo occuparmi quando si passa al nuovo tipo di stringa (diverso dall'ovvia base 0 vs 1)?Delphi XE4 stringhe immutabili

+0

Si noti che è un commutatore se le stringhe sono a base zero. Certamente non è una buona idea mescolare entrambi i modi, ma almeno puoi decidere da solo quando effettuare la transizione. – jpfollenius

+0

Si suppone che usiamo la classe 'TStringBuilder' per la manipolazione delle stringhe e' TStringHelper' per la gestione generale delle stringhe. –

+0

Il tipo 'String' stesso è in realtà lo stesso di prima, è solo l'operatore' [] 'che è interessato. Immutabilità significa semplicemente che il compilatore non consente l'assegnazione di un 'Char' all'operatore, e la direttiva' {$ ZEROBASEDSTRINGS} 'influisce solo su come il compilatore interpreta gli indici che vengono passati all'operatore. Il tipo 'String' non è stato ridisegnato. –

risposta

17

Secondo Marco Cantù's whitepaper, il tipo di dati string nel target XE4 iOS non è in effetti immutabile, sebbene sembri contraddire.

Egli dice:

Nel nuovo compilatore Delphi LLVM-based, c'è un tipo di stringa, che rappresenta le stringhe Unicode (UTF16), e mappato al tipo stringa corrente in Delphi XE3 (un alias per il Tipo UnicodeString sul compilatore di Windows). Tuttavia, questo nuovo tipo di stringa utilizza un diverso modello di gestione della memoria. Il tipo di stringa è ancora conteggiato con riferimento, ma è immutabile, il che significa che non è possibile modificare il contenuto della stringa una volta creata.

ma poi continua a dire:

In altre parole stringhe sono ora basati su Unicode , in procinto di diventare immutabile, e il riferimento-contati.

E anche:

Dove le cose cominciano a cambiare, però, è quando si modifica un stringa esistente, non sostituendolo con un nuovo valore (nel qual caso si ottiene un nuovo di zecca stringa), ma quando si modifica uno dei suoi elementi, come mostrato in questa riga di codice (e anche nella sezione precedente, dove ho introdotto il tema):

Str1 [3] := 'x'; 

Tutti i compilatori Delphi utilizzano una semantica copy-on-write: se la stringa che si modifica ha più di un riferimento, viene prima copiata (regolando i conteggi di riferimento delle varie stringhe necessarie) e modificato in seguito.

Il nuovo compilatore fa qualcosa di molto simile a quello classico. Esso implementa un meccanismo di copia su scrittura, a meno che non vi sia un singolo riferimento alla stringa, nel qual caso la stringa viene modificata in posizione. Ad esempio, prendere in considerazione il seguente codice, che emette la posizione in memoria della stringa effettiva in .

E poi mostra un'immagine di un dispositivo iOS con stringhe mutanti.

E nel official documentation abbiamo:

stringhe sono immutabili (costante), quindi non si può indice in una stringa come un array e manipolare i caratteri di una stringa. Se si prova a modificare una stringa, i compilatori mobili Delphi potrebbero emettere il messaggio W1068 La modifica delle stringhe in essere potrebbe non essere supportata in futuro (Delphi).È possibile specificare se il messaggio x1068 viene emesso come un avviso o un errore. Nella pagina Suggerimenti e avvertenze, impostare l'avviso "Modifica stringhe sul posto ...." su "true" o "errore".

Quindi interpreto tutto ciò nel senso che la versione XE4 del compilatore iOS ha ancora stringhe mutabili. Gli sviluppatori non vogliono più che tu muti le tue stringhe e ti stanno dicendo che le stringhe sono immutabili sui compilatori mobili. Ma sembrano ancora mutabili. Vai a capire!


Tuttavia, è stato notificato che in una versione futura, la stringa potrebbe diventare immutabile.

È possibile prepararsi per quel versione futura ora impostando

{$WARN IMMUTABLE_STRINGS WARN} 

che vi darà un'idea dell'impatto del cambiamento. Se si vuole allacciare le cinture e smettere di mutare le stringhe, si può fare questo:

{$WARN IMMUTABLE_STRINGS ERROR} 

Una volta fatto questo è necessario convertire il codice che accede a singoli elementi di stringa. Sospetto che sarai sorpreso da quanto poco codice ci sia. Ho appena compilato 600.000 righe di codice e ho visto solo 120 istanze dell'avvertimento. E la maggior parte di quelli erano in unità di terze parti. Ho visto molto scalpore per questo cambiamento, ma onestamente non credo che molto codice muta le stringhe. Nella stragrande maggioranza dei casi le stringhe sono create mediante concatenazione o chiamate a funzioni come Format. Questo codice non è influenzato da questo.

Non penso ci siano grandi insidie. È possibile utilizzare {$WARN IMMUTABLE_STRINGS ...} per consentire al compilatore di guidare l'utente attraverso il processo. Qualsiasi codice che muti le stringhe deve essere convertito per utilizzare TStringBuilder.

Per quanto riguarda i benefici di immutabilità, vi rimando a Why .NET String is immutable?

Se si utilizzano i tradizionali compilatori Windows o OSX poi vedo alcuna ragione per cambiare. Il compilatore iOS è nuovo di zecca. La modifica alle stringhe immutabili è stata fluttuata, ma potrebbe non succedere mai. Può accadere solo sui compilatori mobili e mai sui compilatori tradizionali. In questo momento, mi siedo stretto, e aspetto di vedere come tutto si svolge.

+3

Tim Anderson è anche confuso su quanto sia immutabile la nuova stringa mobile immutabile davvero: http://www.itwriting.com/blog/7347-changes-in-the-delphi-language-for-arm-and-mobile- support.html –

+3

Woah, ho un po 'paura di saltare alle conclusioni, ma questa sembra un'altra cattiva idea degli sviluppatori Delphi. Interrompiamo la compatibilità per rendere le stringhe meno utili, un ottimo piano. – himself

+3

@himself Ci sono vantaggi con l'immutabilità. E in ogni caso, è un cambiamento di impatto molto basso. Trascurando le librerie di terze parti con cui si occuperà qualcun altro, potrei sistemare il mio codebase in circa un'ora.Preferirei che venisse rimosso un po 'del codice della lingua, anche se ciò significa un po' di dolore dalla nostra parte. –

Problemi correlati