Existe-t-il une manière native Swift pour tout nombre (au moins entier) d'obtenir sa représentation hexadécimale dans une chaîne? Et l'inverse. Elle ne doit pas utiliser Foundation. Par exemple, la classe String a une fonction
func toInt() -> Int?
qui convertit une chaîne représentant un entier en sa valeur Int. Je cherche quelque chose de similaire, en utilisant les chaînes hexadécimales. Je sais que cela est facilement implémentable, mais si Swift l'a déjà là, ce serait mieux. Sinon, si vous avez déjà fait une extension de String et Int pour atteindre les objectifs suivants:
let anHex = "0xA0"
if let anInt = anHex.toInt() {
println(anInt) // prints 128
println(anInt.toHexString()) // prints "0xA0"
}
Je sais que ce n'est pas sorcier, mais au cas où je vous en prie, partagez-le.
PS: Ceci est similaire à cette question , la différence est qu'il était très lié au framework Foundation, alors que je ne l'utilise pas dans mon code (ni que j'importe quoi d'autre) et pour l'instant je Je voudrais le conserver de cette manière, également à des fins d'apprentissage.
Depuis Swift 2, tous les types entiers ont un constructeur
init?(_ text: String, radix: Int = default)
de sorte que les conversions d'entier en chaîne hexadécimale et de chaîne hexadécimale en entier puissent être effectuées avec des méthodes intégrées. Exemple:
let num = 1000
let str = String(num, radix: 16)
print(str) // "3e8"
if let num2 = Int(str, radix: 16) {
print(num2) // 1000
}
(Ancienne réponse pour Swift 1:) La conversion d'un entier en une chaîne hexadécimale peut être effectuée avec
let hex = String(num, radix: 16)
(voir par exemple Comment convertir un nombre décimal en binaire dans Swift? ). Cela ne nécessite l'importation d'aucun Framework et fonctionne avec n'importe quelle base entre 2 et 36.
La conversion d'une chaîne hexadécimale en un entier peut être effectuée avec la fonction de bibliothèque BSD strtoul()
(comparer Comment convertir un binaire en décimal dans Swift? ) si vous êtes prêt à import Darwin
.
Sinon, il n'y a (pour autant que je sache) pas de méthode intégrée Swift. Voici une extension qui convertit une chaîne en nombre selon une base donnée:
extension UInt {
init?(_ string: String, radix: UInt) {
let digits = "0123456789abcdefghijklmnopqrstuvwxyz"
var result = UInt(0)
for digit in string.lowercaseString {
if let range = digits.rangeOfString(String(digit)) {
let val = UInt(distance(digits.startIndex, range.startIndex))
if val >= radix {
return nil
}
result = result * radix + val
} else {
return nil
}
}
self = result
}
}
Exemple:
let hexString = "A0"
if let num = UInt(hexString, radix: 16) {
println(num)
} else {
println("invalid input")
}
mise à jour: Xcode 7.2 • Swift 2.1.1
extension String {
var drop0xPrefix: String { return hasPrefix("0x") ? String(characters.dropFirst(2)) : self }
var drop0bPrefix: String { return hasPrefix("0b") ? String(characters.dropFirst(2)) : self }
var hexaToDecimal: Int { return Int(drop0xPrefix, radix: 16) ?? 0 }
var hexaToBinaryString: String { return String(hexaToDecimal, radix: 2) }
var decimalToHexaString: String { return String(Int(self) ?? 0, radix: 16) }
var decimalToBinaryString: String { return String(Int(self) ?? 0, radix: 2) }
var binaryToDecimal: Int { return Int(drop0bPrefix, radix: 2) ?? 0 }
var binaryToHexaString: String { return String(binaryToDecimal, radix: 16) }
}
extension Int {
var toBinaryString: String { return String(self, radix: 2) }
var toHexaString: String { return String(self, radix: 16) }
}
Essai:
print("7fffffffffffffff".hexaToDecimal) // "9223372036854775807" decimal integer
print("0x7fffffffffffffff".hexaToDecimal) // "9223372036854775807" decimal integer
print("7fffffffffffffff".hexaToBinaryString) // "111111111111111111111111111111111111111111111111111111111111111" binary (String)
print("0x7fffffffffffffff".hexaToBinaryString) // "111111111111111111111111111111111111111111111111111111111111111"
print("255".decimalToHexaString) // "ff" hexa (String)
print("255".decimalToBinaryString) // "11111111" binary (String)
0b11111111
print("11111111".binaryToHexaString) // "ff" hexa (String)
print("0b11111111".binaryToHexaString) // "ff" hexa (String)
print("11111111".binaryToDecimal) // 255 decimal (Int)
print("0b11111111".binaryToDecimal) // 255 decimal (Int)
print(255.toBinaryString) // "11111111" binary (String)
print(255.toHexaString) // "ff" hexadecimal (String)
String
à UInt
:let str = "fcd7d7"
let number = UInt(str, radix: 16)!
print(number)
résultat: 16570327
UInt
en hex String
:let number = UInt(exactly: 16570327)!
let str = String(number, radix: 16, uppercase: false)
print(str)
résultat: fcd7d7
Pour Float, Si vous souhaitez que le point flottant IEEE754 soit HEX
extension Float {
func floatToHex()->String {
return String(self.bitPattern, radix: 16, uppercase: true)
}
}
let f:Float = 3.685746e+19
let hex = f.floatToHex()
print("\(hex)")//5FFFC000
Ou Visa-versa
extension String {
func hexToFloat() -> Float {
var toInt = Int32(truncatingBitPattern: strtol(self, nil, 16))
var toInt = Int32(_truncatingBits: strtoul(self, nil, 16)) //For Swift 5
var float:Float32!
memcpy(&float, &toInt, MemoryLayout.size(ofValue: float))
return float
}
}