2014-09-16 15 views
7

Sembra che le divisioni intere in Swift ruotino verso zero anziché verso il numero più basso. Ciò significa, ad esempio, che -1/2 sarà 0 anziché -1.Quoziente intero negativo rotondo verso l'infinito negativo

C'è un modo per dire a Swift di arrotondare verso il numero più basso? So come posso "simularlo", ma se c'è una soluzione nativa, preferisco usarla.

risposta

0

La funzione del piano si arrotonda per cui se si esegue floor(Float(a)/Float(b)) dovrebbe funzionare.

+1

Questo sarebbe 'Int (floor (Float (a)/Float (b)))', comunque. Sicuramente non per i deboli di cuore. – zneak

1

È possibile definire il proprio operatore come questo:

infix operator </> { associativity left } 
func </> (a: Int, b: Int) -> Int { 
    return Int(floor(Double(a)/Double(b))) 
} 

in modo da non dover digitare l'espressione assurda. Sto proponendo </>, ma ovviamente puoi scegliere il tuo.

Se non ti piace la creazione di operatori, quindi utilizzarlo come una normale funzione:

func div (a: Int, b: Int) -> Int { 
    return Int(floor(Double(a)/Double(b))) 
} 

Ultimo, ma personalmente avrei non usarlo, è possibile ridefinire l'operatore di divisione:

func/(a: Int, b: Int) -> Int { 
    return Int(floor(Double(a)/Double(b))) 
} 

e in questo caso sarà applicato a tutte le divisioni - essere consapevoli degli effetti collaterali se

0

La soluzione di backup che ho riguarda un nuovo operatore -/. La matematica non prevede lo shuffling avanti e indietro tra i doppi e gli interi, il che evita alcuni casi limite con numeri molto grandi. D'altra parte, questo può overflow invece se sia denominator e numerator sono numeri negativi molto grandi, e non sono sicuro di cosa succede esattamente se denominator è negativo.

infix operator -/ { 
    precedence 150 
    associativity left 
} 

func -/ (numerator: Int, denominator: Int) -> Int { 
    if numerator < 0 { 
     return (numerator - (denominator - 1))/denominator 
    } 
    return numerator/denominator 
} 

Qualsiasi soluzione scritta in termini di Swift probabilmente finire con la sua quota di problemi, se si desidera emulare il comportamento C. Un'altra possibilità sarebbe includere una piccola funzione divide nell'intestazione del bridging e implementare con essa l'operatore.