2016-01-25 14 views
8

Sappiamo che un Duff's device fa uso di interlacciamento delle strutture di un interruttore falltrough e un ciclo come:di Duff a Swift

send(to, from, count) 
register short *to, *from; 
register count; 
{ 
    register n = (count + 7)/8; 
    switch (count % 8) { 
    case 0: do { *to = *from++; 
    case 7:  *to = *from++; 
    case 6:  *to = *from++; 
    case 5:  *to = *from++; 
    case 4:  *to = *from++; 
    case 3:  *to = *from++; 
    case 2:  *to = *from++; 
    case 1:  *to = *from++; 
      } while (--n > 0); 
    } 
} 

Ora, in Swif 2.1, switch-case control flows non lo fanno implicitamente hanno falltrough come si legge nella docs Swift:

No implicito falltrough

in contrasto con le istruzioni switch in C e Objective-C, l'interruttore dichiarazioni a Swift non fare t cadere attraverso il fondo di ogni caso e nel prossimo per impostazione predefinita. Invece, l'intera istruzione switch termina la sua esecuzione non appena il primo caso switch corrispondente è completato, senza richiedere un'istruzione esplicita di interruzione. Ciò rende l'istruzione switch più sicura e più facile da usare rispetto a C, ed evita che esegua per errore più di un caso switch.

Ora, dato che c'è una clausola falltrough di avere esplicitamente un effetto collaterale falltrough a Swift:

falltrough

istruzioni switch a Swift non cadono attraverso il fondo di ciascun caso e nel prossimo. Invece, l'intera istruzione switch completa la sua esecuzione non appena il primo caso corrispondente è stato completato. Con il contrasto , C richiede di inserire un'istruzione esplicita sull'interruzione di di ogni caso di commutazione per impedire il fallthrough. Evitare il default di default significa che le istruzioni di switch Swift sono molto più concise e prevedibili rispetto alle loro controparti in C, e quindi evitano per errore l'esecuzione di più casi di switch.

che è più o meno simile:

let integerToDescribe = 5 
var description = "The number \(integerToDescribe) is" 
switch integerToDescribe { 
case 2, 3, 5, 7, 11, 13, 17, 19: 
    description += " a prime number, and also" 
    fallthrough 
default: 
    description += " an integer." 
} 
print(description) 
// prints "The number 5 is a prime number, and also an integer." 

se si considera che, come Wikipedia ricorda di noi, i dispositivi esce dalla questione

A straightforward code to copy items from an array to a memory-mapped output register might look like this: 
do {       /* count > 0 assumed */ 
    *to = *from++;   /* "to" pointer is NOT incremented, see explanation below */ 
} while(--count > 0); 

Che sarebbe l'esatto implementazione di un Il dispositivo di Duff in Swift?

Questa è solo una domanda di codifica del linguaggio &, non è pensata per essere applicata nelle applicazioni Swift reali.

+0

falltrough è un aspetto essenziale del dispositivo di Duff. Senza di esso, non penso esista un'implementazione esatta in Swift. In Swift, non è nemmeno possibile simulare il fallthrough in un'istruzione Switch, quindi è necessario utilizzare una serie di 'if then'statements invece. Non ha molto senso, penso. –

+4

Eh ... questa è un'ottimizzazione del 1983. Cose come le memorie cache e la previsione dei rami sono state inventate a malapena, per non parlare delle implementazioni 'memcpy' altamente ottimizzate. Perché ottimizzi il codice secondo un algoritmo degli anni '80 e perché pensi che queste cose siano ancora attuali oggi? – Lundin

+0

solo una domanda di codice/lingua, non una vera implementazione per qualcosa che dovrebbe essere rilevante oggi. – loretoparisi

risposta

1

Esprimi il tuo intento nel codice di livello più alto possibile e fidati del compilatore Swift per ottimizzarlo per te, invece di provare a ottimizzarlo da solo. Swift è un linguaggio di alto livello. Non esegui lo srotolamento del ciclo a basso livello in un linguaggio di alto livello.

E in Swift, in particolare, non devi preoccuparti di copiare gli array (l'applicazione originale del dispositivo Duff) perché Swift finge di copiare un array ogni volta che lo assegni, usando "copia su scrittura". Ciò significa che utilizzerà lo stesso array per due variabili purché si stia leggendo da esse, ma non appena ne modifichi uno, creerà un duplicato in background.

Ad esempio, da https://developer.apple.com/documentation/swift/array Modifica copie degli array

Each array has an independent value that includes the values of all 
of its elements. For simple types such as integers and other structures, 
this means that when you change a value in one array, the value of that 
element does not change in any copies of the array. For example: 

var numbers = [1, 2, 3, 4, 5] 
var numbersCopy = numbers 
numbers[0] = 100 
print(numbers) 
// Prints "[100, 2, 3, 4, 5]" 
print(numbersCopy) 
// Prints "[1, 2, 3, 4, 5]"