2015-03-21 26 views
71

Sto cercando di convertire questo codice Obj-C nel codice Swift ma non so quale dovrebbe essere l'equivalente di questo codice?Come posso convertire da gradi a radianti?

#define DEGREES_TO_RADIANS(degrees)((M_PI * degrees)/180) 

I Googled e trovato this

Ma io non capisco come convertire che nel Swift nel mio caso?

+0

Penso che si sta perdendo un po 'di codice. Puoi aggiungere tutti i codici rilevanti? Qualsiasi altro definisce, come i gradi? – BlackHatSamurai

+0

questo è il mio codice swift: http: //pastebin.com/bZ4a7EVN –

+0

Puoi mostrarmi il tuo file .h? – BlackHatSamurai

risposta

184

Xcode 9 • Swift 4

extension BinaryInteger { 
    var degreesToRadians: CGFloat { return CGFloat(Int(self)) * .pi/180 } 
} 

extension FloatingPoint { 
    var degreesToRadians: Self { return self * .pi/180 } 
    var radiansToDegrees: Self { return self * 180/.pi } 
} 

giochi

45.degreesToRadians   // 0.785398163397448 

Int(45).degreesToRadians // 0.785398163397448 
Int8(45).degreesToRadians // 0.785398163397448 
Int16(45).degreesToRadians // 0.785398163397448 
Int32(45).degreesToRadians // 0.785398163397448 
Int64(45).degreesToRadians // 0.785398163397448 

UInt(45).degreesToRadians // 0.785398163397448 
UInt8(45).degreesToRadians // 0.785398163397448 
UInt16(45).degreesToRadians // 0.785398163397448 
UInt32(45).degreesToRadians // 0.785398163397448 
UInt64(45).degreesToRadians // 0.785398163397448 

Double(45).degreesToRadians // 0.7853981633974483 
CGFloat(45).degreesToRadians // 0.785398163397448 
Float(45).degreesToRadians  // 0.7853981 
Float80(45).degreesToRadians // 0.785398163397448278999 
+2

Non dovresti estendere 'CGFloat'? – Zorayr

+1

@Zorayr aggiornato a Swift 3 e l'estensione di FloatingPoint ora li estende tutti –

+2

In realtà, in Swift 3 è possibile utilizzare i tipi di misurazione e non è necessario conoscere la formula di conversione! – matt

35

Apple fornisce questi GLKit functions per la conversione:

func GLKMathDegreesToRadians(_ degrees: Float) -> Float 
func GLKMathRadiansToDegrees(_ radians: Float) -> Float 
8

Inoltre, per convertire fron radianti in gradi (se qualcuno inciampa su questo su google):

var degrees = radians * (180.0/M_PI) 
3

Non sei più limitato a caratteri ASCII per la creazione di nomi di variabili, in modo da come su questo con π (alt -p): utilizzo

typealias RadianAngle = CGFloat 

let π = RadianAngle(M_PI) 
let π_x_2 = RadianAngle(M_PI * 2) 
let π_2 = RadianAngle(M_PI_2) 
let π_4 = RadianAngle(M_PI_4) 

extension RadianAngle { 
    var degrees: CGFloat { 
     return self * 180/π 
    } 
    init(degrees: Int) { 
     self = CGFloat(degrees) * π/180 
    } 
} 

Esempio:

let quarterCircle = RadianAngle(degrees: 90) 
print("quarter circle = \(quarterCircle) radians") 
// quarter circle = 1.5707963267949 radians 

let halfCircle = π 
print("half circle = \(halfCircle.degrees) degrees") 
// half circle = 180.0 degrees 
29

Questo non è identico quello che hai chiesto, ma a Swift 3/iOS 10, è possibile utilizzare la misura digita e fai la conversione senza conoscere la formula!

let result = Measurement(value: 45, unit: UnitAngle.degrees) 
    .converted(to: .radians).value 
+2

Incredibile @matt al lavoro di nuovo, grazie! Sfortunatamente solo iOS 10. –

12
let angle = 45° // angle will be in radians, 45 is in degrees 

compila sotto Swift 3. Conserva ancora tutti i valori, fai tutti i calcoli in radianti con CGFloats ..., ma rendi il codice più leggibile con le costanti in gradi. Ad esempio: 90 ° Il simbolo ° esegue magicamente la conversione dei gradi in radianti.

Come impostare questa funzione:

Definire e utilizzare un operatore di postfix per il segno °. Questo operatore farà la conversione da gradi a radianti. Questo esempio è per Ints, estendilo anche per i tipi Float se ne hai la necessità.

postfix operator ° 

protocol IntegerInitializable: ExpressibleByIntegerLiteral { 
    init (_: Int) 
} 

extension Int: IntegerInitializable { 
    postfix public static func °(lhs: Int) -> CGFloat { 
    return CGFloat(lhs) * .pi/180 
    } 
} 

Alcuni esempi di utilizzo:

let angle = 45° 

contentView.transform = CGAffineTransform(rotationAngle: 45°) 

let angle = 45 
contentView.transform = CGAffineTransform(rotationAngle: angle°) 

Attenzione!

È troppo facile utilizzare questa conversione due volte (su un valore già in radianti per errore), si otterrà un numero molto piccolo come risultato, e apparentemente l'angolo risultante sarà sempre pari a zero ... NON usare ° sullo stesso valore due volte (non convertire due volte) !!:

// OBVIOUSLY WRONG! 
let angle = 45°° // ° used twice here 

// WRONG! BUT EASY TO MISS 
let angle = 45° // ° used here 
contentView.transform = CGAffineTransform(rotationAngle: angle°) // ° also used here 
0

userei lo stesso principio @ t1ser di cui sopra, ma creare un'estensione di CGFloat per rendere più facile da usare decimali per il grado e (così si potrebbe avere un 23,4 gradi, per esempio) :

extension CGFloat { 
    func degrees() -> CGFloat { 
     return self * .pi/180 
    } 

    init(degrees: CGFloat) { 
     self = degrees.degrees() 
    } 
} 

Utilizzando sarebbe piuttosto facile così (soprattutto perché io personalmente non sapevo come digitare ° - nel caso non lo sia, è option+shift+8 btw):

let degreesToConvert: CGFloat = 45.7 
. 
. 
. 
let convertedDegrees = degreesToConvert.degrees() 

O per usare l'initialiser:

let convertedDegrees = CGFloat(degrees: 45.3) 
0

rapida 2,3

func kilometersBetween(Place1:CLLocationCoordinate2D , Place2:CLLocationCoordinate2D) -> Double{ 
    var start = MKMapPointForCoordinate(Place1) 
    var finish = MKMapPointForCoordinate(Place2) 
    print(MKMetersBetweenMapPoints(start, finish)/1000) 
    return MKMetersBetweenMapPoints(start, finish)/1000 
} 
Problemi correlati