[Swift]实际编程过程中的技巧整理(待更新)

1.Swift中,将Byte类型转化成char类型

例:

let b:Byte = 97

println(Character(UnicodeScalar(Int(b))))

当然可以扩展Byte类

extension Byte {
    func char() -> Character {
        return Character(UnicodeScalar(Int(self)))
    }
}

println(b.char())   // prints "a"
println(98.char())  // prints "b"

2.Using Structs (includes byte Array) with SWIFT - Struct to NSData and NSData to Struct


这是在stackoverflow上查问题时发现的,整理下以备后用。

这是楼主的问题:

I'm now finding that if I have a struct with bytes mixes with a byte array it doesn't pack correctly.

Example Code:

struct exampleStruct {
    var ModelNumber: Byte
    var MajorVersion: Byte
    var MinorVersion: Byte
    var Revision: Byte
    var Message: [Byte]
}

var myStruct = exampleStruct (
    ModelNumber: 1,
    MajorVersion: 2,
    MinorVersion: 3,
    Revision: 4,
    Message: [0x48, 0x45, 0x4C, 0x4C, 0x4F] // HELLO
)

println(myStruct.Message) returns correct array with values of [72,69,76,76,79]

However, when I convert this struct to NSData using:

// Struct to NSData.
var data = NSData(
    bytes: & myStruct,
    length: sizeof(exampleStruct)
)

I get unexpected results of: "data: <01020304 00000000 108c91fd a87f0000>". I was expecting "data: <01020304 48454c4c 4f>"

It seems like this is because the [Byte] Array length is not set. Can it be set in SWIFT? When I try the following:

struct exampleStruct {
   var ModelNumber: Byte
   var MajorVersion: Byte
   var MinorVersion: Byte
   var Revision: Byte
   var Message: Byte[5] // << Set array length 5
}

I get a warning that states: "Fixed-length arrays are not yet supported".

Anyway to work around this limitation?

以下是解决方案:

var Message: [Byte] declares a variable of the type struct Array:

struct Array<T> : MutableCollectionType, Sliceable {

    /// The type of element stored by this `Array`
    typealias Element = T

    /// Always zero, which is the index of the first element when non-empty.
    var startIndex: Int { get }

    /// A "past-the-end" element index; the successor of the last valid
    /// subscript argument.
    var endIndex: Int { get }
    subscript (index: Int) -> T

    // ... and much more ...
}

so this is not just a "C array" of bytes. The actual storage is opaque and only accessible through methods and properties.

You can define a tuple of fixed size:

struct exampleStruct {
    var ModelNumber: Byte
    var MajorVersion: Byte
    var MinorVersion: Byte
    var Revision: Byte
    var Message: (Byte, Byte, Byte, Byte, Byte)
}

var myStruct = exampleStruct (
    ModelNumber: 1,
    MajorVersion: 2,
    MinorVersion: 3,
    Revision: 4,
    Message: (0x48, 0x45, 0x4C, 0x4C, 0x4F) // HELLO
)
var data = NSData(
    bytes: &myStruct,
    length: sizeof(exampleStruct)
)

println(data) // <01020304 48454c4c 4f>

However, I don't think that Swift makes any guarantees about the binary representation of its structures, so this may break in the future.

3.NSData from Byte array in Swift (NSData用[Byte]初始化)

这是楼主的问题:

I'm trying to create an NSData var from an array of bytes.

In Obj-C I might have done this:

NSData *endMarker = [[NSData alloc] initWithBytes:{ 0xFF, 0xD9 }, length: 2]

I can't figure out a working equivalent in Swift.

以下是解决方案:

一、

NSData has an init method that looks like init(bytes: ConstUnsafePointer<()>, length: Int). A ConstUnsafePointer parameter can accept a variety of different things, including a simple Swift array, so you can use pretty much the same syntax as in Objective-C. When you pass the array, you need to make sure you identify it as a Byte array or Swift's type inference will assume you mean to create an Int array.

var endMarker = NSData(bytes: [0xFF, 0xD9] as [Byte], length: 2)

You can read more about unsafe pointer parameters in Apple's Interacting with C APIsdocumentation.

二、

var foo : Byte[] = [0xff, 0xD9]

var data = NSData(bytes: foo, length: foo.count)

println("\(data)")

outputs: ff d9

var data = NSData(bytes: [0xFF, 0xD9] as Byte[], length: 2)

println("\(data)")

outputs: ff d9

Edit: Ah, you have to write 'as Byte[]', so then the results are the same

4.Create an Array in Swift from an NSData Object(在Swift中将一个NSData数据与数组相互转换)

一、将一个UInt32数组转换成NSData

import Foundation

var arr : UInt32[] = [32,4,123,4,5,2];

let data = NSData(bytes: arr, length: arr.count * sizeof(UInt32))

println(data)  //data looks good in the inspector

// now get it back into an array?
二、这是将NSData数据转换成UInt32数组。

使用了NSData中的getBytes(……)这个函数。

// the number of elements:
let count = data.length / sizeof(UInt32)

// create array of appropriate length:
var array = [UInt32](count: count, repeatedValue: 0)

// copy bytes into array
data.getBytes(&array, length:count * sizeof(UInt32))

println(array)
// Output: [32, 4, 123, 4, 5, 2]



你可能感兴趣的:(swift)