Swift中使用C11标准的原子操作

当前Swift 3.0中还没有正式引入基本类型相对应的原子类型。而在macOS以及iOS下,我们可以用系统自带的OSAtomic API进行原子操作处理。但这组API只能在Apple自家平台上使用,我们无法在Linux/FreeBSD中使用,所以我这边封装了顺应C11标准的一组原子类型与原子操作提供给Swift编程语言。


当前在Swift中,如果我们在C语言头文件声明了一个比如atomic_int类型的全局对象,那么该对象在Swift中是无法被导入的,因为atomic_int类型在Swift中无法被转换为它所能识别的相应类型。所以,我这边的思路是将C11标准中支持的原子类型通过结构体进行封装。我在下列代码中封装了3种原子类型,分别为:atomic_int、atomic_bool以及atomic_uint_fast64_t,分别表示int原子类型、布尔原子类型以及无符号64位整数原子类型。我这边建立的项目名为SwiftTest,所以Swift所需要的桥接头文件名为SwiftTest-Bridging-Header.h。下面先给出此头文件的完整源代码:

#include <stdint.h>
#include <stdbool.h>
#include <stdatomic.h>

/** 用于Swift的AtomicInt原子类型 */
struct AtomicIntSwift {
    volatile atomic_int atom;
};

/**
 * 对原子对象进行初始化
 * @param pAtom 指向Swift中AtomicInt类型的原子对象,并且不允许为空
 * @param value 指定要给原子对象初始化的值
*/
extern void __attribute__((overloadable)) AtomicSwiftInit(struct AtomicIntSwift* __nonnull pAtom, int value);

/**
 * 对原子对象进行加载操作
 * @param pAtom 指向Swift中AtomicInt类型的原子对象,并且不允许为空
 * @return 指定原子对象所存储的值
*/
extern int __attribute__((overloadable)) AtomicSwiftLoad(struct AtomicIntSwift* __nonnull pAtom);

/** 
 * 对原子对象进行存储操作
 * @param pAtom 指向Swift中AtomicInt类型的原子对象,并且不允许为空
 * @param value 要存储到指定原子对象中的值
*/
extern void __attribute__((overloadable)) AtomicSwiftStore(struct AtomicIntSwift* __nonnull pAtom, int value);

/**
 * 将原子对象中存放的值与所指定的基本类型的值进行交换。
 *
 * 也就是说,将基本类型的值存放到原子对象中去,并将原子对象的原始值返回
 * @param pAtom 指向Swift中AtomicInt类型的原子对象,并且不允许为空
 * @param value 指定的基本类型的值
 * @return 原子对象的原始值
*/
extern int __attribute__((overloadable)) AtomicSwiftExchange(struct AtomicIntSwift* __nonnull pAtom, int value);

/**
 * 原子比较与交换
 *
 * 将原子对象中的值与expected的值进行比较,如果相同则将desired的值写入到原子对象中,并返回true;
 * 否则,将当前原子对象中的值写入到expected中去,并返回false
 * @param pAtom 指向Swift中AtomicInt类型的原子对象,并且不允许为空
 * @param expected 存放与原子对象进行比较的值的指针。
 *                 该指针一般指向用原子加载操作所得到值的变量,并且不能为空。
 * @param desired 要存入到原子对象中的值
 * @return 如果expected中的值与原子对象中所存放的值相同,则返回true,否则返回false
*/
extern bool __attribute__((overloadable)) AtomicSwiftCAS(struct AtomicIntSwift* __nonnull pAtom, int* __nonnull expected, int desired);

/**
 * 原子加法操作
 * @param pAtom 指向Swift中AtomicInt类型的原子对象,并且不允许为空
 * @param value 指定的基本类型的值
 * @return 原子对象的原始值
*/
extern int __attribute__((overloadable)) AtomicSwiftFetchAdd(struct AtomicIntSwift* __nonnull pAtom, int value);

/**
 * 原子减法操作
 * @param pAtom 指向Swift中AtomicInt类型的原子对象,并且不允许为空
 * @param value 指定的基本类型的值
 * @return 原子对象的原始值
*/
extern int __attribute__((overloadable)) AtomicSwiftFetchSub(struct AtomicIntSwift* __nonnull pAtom, int value);

/**
 * 原子按位或操作
 * @param pAtom 指向Swift中AtomicInt类型的原子对象,并且不允许为空
 * @param value 指定的基本类型的值
 * @return 原子对象的原始值
*/
extern int __attribute__((overloadable)) AtomicSwiftFetchOr(struct AtomicIntSwift* __nonnull pAtom, int value);

/**
 * 原子按位异或操作
 * @param pAtom 指向Swift中AtomicInt类型的原子对象,并且不允许为空
 * @param value 指定的基本类型的值
 * @return 原子对象的原始值
*/
extern int __attribute__((overloadable)) AtomicSwiftFetchXor(struct AtomicIntSwift* __nonnull pAtom, int value);

/**
 * 原子按位与操作
 * @param pAtom 指向Swift中AtomicInt类型的原子对象,并且不允许为空
 * @param value 指定的基本类型的值
 * @return 原子对象的原始值
*/
extern int __attribute__((overloadable)) AtomicSwiftFetchAnd(struct AtomicIntSwift* __nonnull pAtom, int value);


/** 用于Swift的AtomicBool原子类型 */
struct AtomicBoolSwift {
    volatile atomic_bool atom;
};

/**
 * 对原子对象进行初始化
 * @param pAtom 指向Swift中AtomicBool类型的原子对象,并且不允许为空
 * @param value 指定要给原子对象初始化的值
*/
extern void __attribute__((overloadable)) AtomicSwiftInit(struct AtomicBoolSwift* __nonnull pAtom, bool value);

/**
 * 对原子对象进行加载操作
 * @param pAtom 指向Swift中AtomicBool类型的原子对象,并且不允许为空
 * @return 指定原子对象所存储的值
*/
extern bool __attribute__((overloadable)) AtomicSwiftLoad(struct AtomicBoolSwift* __nonnull pAtom);

/**
 * 对原子对象进行存储操作
 * @param pAtom 指向Swift中AtomicBool类型的原子对象,并且不允许为空
 * @param value 要存储到指定原子对象中的值
 */
extern void __attribute__((overloadable)) AtomicSwiftStore(struct AtomicBoolSwift* __nonnull pAtom, bool value);

/**
 * 将原子对象中存放的值与所指定的基本类型的值进行交换。
 *
 * 也就是说,将基本类型的值存放到原子对象中去,并将原子对象的原始值返回
 * @param pAtom 指向Swift中AtomicBool类型的原子对象,并且不允许为空
 * @param value 指定的基本类型的值
 * @return 原子对象的原始值
*/
extern bool __attribute__((overloadable)) AtomicSwiftExchange(struct AtomicBoolSwift* __nonnull pAtom, bool value);

/**
 * 原子比较与交换
 *
 * 将原子对象中的值与expected的值进行比较,如果相同则将desired的值写入到原子对象中,并返回true;
 * 否则,将当前原子对象中的值写入到expected中去,并返回false
 * @param pAtom 指向Swift中AtomicBool类型的原子对象,并且不允许为空
 * @param expected 存放与原子对象进行比较的值的指针。
 *                 该指针一般指向用原子加载操作所得到值的变量,并且不能为空。
 * @param desired 要存入到原子对象中的值
 * @return 如果expected中的值与原子对象中所存放的值相同,则返回true,否则返回false
*/
extern bool __attribute__((overloadable)) AtomicSwiftCAS(struct AtomicBoolSwift* __nonnull pAtom, bool* __nonnull expected, bool desired);


/** 用于Swift的AtomicULong原子类型 */
struct AtomicULongSwift {
    volatile atomic_uint_fast64_t atom;
};

/**
 * 对原子对象进行初始化
 * @param pAtom 指向Swift中AtomicULong类型的原子对象,并且不允许为空
 * @param value 指定要给原子对象初始化的值
*/
extern void __attribute__((overloadable)) AtomicSwiftInit(struct AtomicULongSwift* __nonnull pAtom, uint64_t value);

/**
 * 对原子对象进行加载操作
 * @param pAtom 指向Swift中AtomicULong类型的原子对象,并且不允许为空
 * @return 指定原子对象所存储的值
*/
extern uint64_t __attribute__((overloadable)) AtomicSwiftLoad(struct AtomicULongSwift* __nonnull pAtom);

/**
 * 对原子对象进行存储操作
 * @param pAtom 指向Swift中AtomicULong类型的原子对象,并且不允许为空
 * @param value 要存储到指定原子对象中的值
*/
extern void __attribute__((overloadable)) AtomicSwiftStore(struct AtomicULongSwift* __nonnull pAtom, uint64_t value);

/**
 * 将原子对象中存放的值与所指定的基本类型的值进行交换。
 *
 * 也就是说,将基本类型的值存放到原子对象中去,并将原子对象的原始值返回
 * @param pAtom 指向Swift中AtomicULong类型的原子对象,并且不允许为空
 * @param value 指定的基本类型的值
 * @return 原子对象的原始值
*/
extern uint64_t __attribute__((overloadable)) AtomicSwiftExchange(struct AtomicULongSwift* __nonnull pAtom, uint64_t value);

/**
 * 原子比较与交换
 *
 * 将原子对象中的值与expected的值进行比较,如果相同则将desired的值写入到原子对象中,并返回true;
 * 否则,将当前原子对象中的值写入到expected中去,并返回false
 * @param pAtom 指向Swift中AtomicULong类型的原子对象,并且不允许为空
 * @param expected 存放与原子对象进行比较的值的指针。
 *                 该指针一般指向用原子加载操作所得到值的变量,并且不能为空。
 * @param desired 要存入到原子对象中的值
 * @return 如果expected中的值与原子对象中所存放的值相同,则返回true,否则返回false
*/
extern bool __attribute__((overloadable)) AtomicSwiftCAS(struct AtomicULongSwift* __nonnull pAtom, uint64_t* __nonnull expected, uint64_t desired);

/**
 * 原子加法操作
 * @param pAtom 指向Swift中AtomicULong类型的原子对象,并且不允许为空
 * @param value 指定的基本类型的值
 * @return 原子对象的原始值
*/
extern uint64_t __attribute__((overloadable)) AtomicSwiftFetchAdd(struct AtomicULongSwift* __nonnull pAtom, uint64_t value);

/**
 * 原子减法操作
 * @param pAtom 指向Swift中AtomicULong类型的原子对象,并且不允许为空
 * @param value 指定的基本类型的值
 * @return 原子对象的原始值
*/
extern uint64_t __attribute__((overloadable)) AtomicSwiftFetchSub(struct AtomicULongSwift* __nonnull pAtom, uint64_t value);

/**
 * 原子按位或操作
 * @param pAtom 指向Swift中AtomicULong类型的原子对象,并且不允许为空
 * @param value 指定的基本类型的值
 * @return 原子对象的原始值
*/
extern uint64_t __attribute__((overloadable)) AtomicSwiftFetchOr(struct AtomicULongSwift* __nonnull pAtom, uint64_t value);

/**
 * 原子按位异或操作
 * @param pAtom 指向Swift中AtomicULong类型的原子对象,并且不允许为空
 * @param value 指定的基本类型的值
 * @return 原子对象的原始值
*/
extern uint64_t __attribute__((overloadable)) AtomicSwiftFetchXor(struct AtomicULongSwift* __nonnull pAtom, uint64_t value);

/**
 * 原子按位与操作
 * @param pAtom 指向Swift中AtomicULong类型的原子对象,并且不允许为空
 * @param value 指定的基本类型的值
 * @return 原子对象的原始值
*/
extern uint64_t __attribute__((overloadable)) AtomicSwiftFetchAnd(struct AtomicULongSwift* __nonnull pAtom, uint64_t value);

上述代码列出了我们后面在Swift中所需要的C语言底层对C11标准原子操作的封装实现。下面我们可以在C源文件(.c文件)中实现这些声明的函数接口。

#include <stdio.h>
#include "SwiftTest-Bridging-Header.h"

#pragma mark - atomic int

void __attribute__((overloadable)) AtomicSwiftInit(struct AtomicIntSwift* __nonnull pAtom, int value)
{
    if(pAtom == NULL)
        return;
    
    atomic_init(&pAtom->atom, value);
}

int __attribute__((overloadable)) AtomicSwiftLoad(struct AtomicIntSwift* __nonnull pAtom)
{
    if(pAtom == NULL)
        return 0;
    
    return atomic_load(&pAtom->atom);
}

void __attribute__((overloadable)) AtomicSwiftStore(struct AtomicIntSwift* __nonnull pAtom, int value)
{
    if(pAtom == NULL)
        return;
    
    atomic_store(&pAtom->atom, value);
}

int __attribute__((overloadable)) AtomicSwiftExchange(struct AtomicIntSwift* __nonnull pAtom, int value)
{
    if(pAtom == NULL)
        return 0;
    
    return atomic_exchange(&pAtom->atom, value);
}

bool __attribute__((overloadable)) AtomicSwiftCAS(struct AtomicIntSwift* __nonnull pAtom, int* __nonnull expected, int desired)
{
    if(pAtom == NULL || expected == NULL)
        return false;
    
    return atomic_compare_exchange_weak(&pAtom->atom, expected, desired);
}

int __attribute__((overloadable)) AtomicSwiftFetchAdd(struct AtomicIntSwift* __nonnull pAtom, int value)
{
    if(pAtom == NULL)
        return 0;
    
    return atomic_fetch_add(&pAtom->atom, value);
}

int __attribute__((overloadable)) AtomicSwiftFetchSub(struct AtomicIntSwift* __nonnull pAtom, int value)
{
    if(pAtom == NULL)
        return 0;
    
    return atomic_fetch_sub(&pAtom->atom, value);
}

int __attribute__((overloadable)) AtomicSwiftFetchOr(struct AtomicIntSwift* __nonnull pAtom, int value)
{
    if(pAtom == NULL)
        return 0;
    
    return atomic_fetch_or(&pAtom->atom, value);
}

int __attribute__((overloadable)) AtomicSwiftFetchXor(struct AtomicIntSwift* __nonnull pAtom, int value)
{
    if(pAtom == NULL)
        return 0;
    
    return atomic_fetch_xor(&pAtom->atom, value);
}

int __attribute__((overloadable)) AtomicSwiftFetchAnd(struct AtomicIntSwift* __nonnull pAtom, int value)
{
    if(pAtom == NULL)
        return 0;
    
    return atomic_fetch_and(&pAtom->atom, value);
}


#pragma mark - atomic bool

void __attribute__((overloadable)) AtomicSwiftInit(struct AtomicBoolSwift* __nonnull pAtom, bool value)
{
    if(pAtom == NULL)
        return;
    
    atomic_init(&pAtom->atom, value);
}

bool __attribute__((overloadable)) AtomicSwiftLoad(struct AtomicBoolSwift* __nonnull pAtom)
{
    if(pAtom == NULL)
        return false;
    
    return atomic_load(&pAtom->atom);
}

void __attribute__((overloadable)) AtomicSwiftStore(struct AtomicBoolSwift* __nonnull pAtom, bool value)
{
    if(pAtom == NULL)
        return;
    
    atomic_store(&pAtom->atom, value);
}

bool __attribute__((overloadable)) AtomicSwiftExchange(struct AtomicBoolSwift* __nonnull pAtom, bool value)
{
    if(pAtom == NULL)
        return false;
    
    return atomic_exchange(&pAtom->atom, value);
}

bool __attribute__((overloadable)) AtomicSwiftCAS(struct AtomicBoolSwift* __nonnull pAtom, bool* __nonnull expected, bool desired)
{
    if(pAtom == NULL || expected == NULL)
        return false;
    
    return atomic_compare_exchange_weak(&pAtom->atom, expected, desired);
}


#pragma mark - atomic uint64_t

void __attribute__((overloadable)) AtomicSwiftInit(struct AtomicULongSwift* __nonnull pAtom, uint64_t value)
{
    if(pAtom == NULL)
        return;
    
    atomic_init(&pAtom->atom, value);
}

uint64_t __attribute__((overloadable)) AtomicSwiftLoad(struct AtomicULongSwift* __nonnull pAtom)
{
    if(pAtom == NULL)
        return 0;
    
    return atomic_load(&pAtom->atom);
}

void __attribute__((overloadable)) AtomicSwiftStore(struct AtomicULongSwift* __nonnull pAtom, uint64_t value)
{
    if(pAtom == NULL)
        return;
    
    atomic_store(&pAtom->atom, value);
}

uint64_t __attribute__((overloadable)) AtomicSwiftExchange(struct AtomicULongSwift* __nonnull pAtom, uint64_t value)
{
    if(pAtom == NULL)
        return 0;
    
    return atomic_exchange(&pAtom->atom, value);
}

bool __attribute__((overloadable)) AtomicSwiftCAS(struct AtomicULongSwift* __nonnull pAtom, uint64_t* __nonnull expected, uint64_t desired)
{
    if(pAtom == NULL || expected == NULL)
        return false;
    
    return atomic_compare_exchange_weak(&pAtom->atom, expected, desired);
}

uint64_t __attribute__((overloadable)) AtomicSwiftFetchAdd(struct AtomicULongSwift* __nonnull pAtom, uint64_t value)
{
    if(pAtom == NULL)
        return 0;
    
    return atomic_fetch_add(&pAtom->atom, value);
}

uint64_t __attribute__((overloadable)) AtomicSwiftFetchSub(struct AtomicULongSwift* __nonnull pAtom, uint64_t value)
{
    if(pAtom == NULL)
        return 0;
    
    return atomic_fetch_sub(&pAtom->atom, value);
}

uint64_t __attribute__((overloadable)) AtomicSwiftFetchOr(struct AtomicULongSwift* __nonnull pAtom, uint64_t value)
{
    if(pAtom == NULL)
        return 0;
    
    return atomic_fetch_or(&pAtom->atom, value);
}

uint64_t __attribute__((overloadable)) AtomicSwiftFetchXor(struct AtomicULongSwift* __nonnull pAtom, uint64_t value)
{
    if(pAtom == NULL)
        return 0;
    
    return atomic_fetch_xor(&pAtom->atom, value);
}

uint64_t __attribute__((overloadable)) AtomicSwiftFetchAnd(struct AtomicULongSwift* __nonnull pAtom, uint64_t value)
{
    if(pAtom == NULL)
        return 0;
    
    return atomic_fetch_and(&pAtom->atom, value);
}

我们看到,这个封装实现其实不是很复杂。为了能让原子操作在Swift中更OO化,我在Swift中将每个原子类型抽象为一个结构体。下面我们来看Swift源文件:

/** 所有原子类型所需遵循的原子类型协议 */

public protocol AtomicType {

    

    /** 当前原子类型所对应的基本类型 */

    associatedtype RawType

    

    /** 初始化器,对当前原子对象初始化为0值。它不具有原子性 */

    init()

    

    /**

     初始化器,对当前原子对象初始化为形参指定的值。它不具有原子性

     

     - parameters:

        - value: 为当前原子对象初始化的初始值

    */

    init(value: RawType)

    

    /**

     加载当前原子对象的值,并返回。

     

     - returns:当前原子对象对应的基本类型的值

    */

    mutatingfunc load() -> RawType

    

    /**

     将一个指定的基本类型值存放到当前原子对象中

     

     - parameters:

        - value: 指定要存放的基本类型的值

    */

    mutatingfunc store(by value: RawType)

    

    /**

     将指定的基本类型的值存入当前原子对象中,并返回存入之前的原子对象的原始值

     

     - parameters:

        - value: 指定的基本类型的值

     

     - returns:在将指定值存入之前的原子对象的原始值

    */

    mutatingfunc exchange(with value: RawType) -> RawType

    

    /**

     原子比较与交换。

     

     

     当前原子对象的值先与expected的值进行比较,如果相同则将desired的值存入当前原子对象,并返回true

     否则将当前原子对象的值存入expected,然后返回false

     

     - parameters:

        - expected: 指向基本类型对象的指针。

                    此基本类型对象在调用该函数前一般会用load方法将当前原子对象的值加载进去。

        - desired: 最终所要写入的值

     

     - returns:如果当前原子对象的值与expected中的值相同,那么返回true,否则返回false

    */

    mutatingfunc cas(expected: UnsafeMutablePointer<RawType>, desired: RawType) ->Bool

    

    /**

     原子加法操作

     

     - parameters:

        - operand: 加法操作数

     

     - returns:加法操作之前原子对象的原始值

    */

    mutatingfunc fetch_add(operand: RawType) -> RawType

    

    /**

     原子减法操作

     

     - parameters:

        - operand: 减法操作数

     

     - returns:减法操作之前原子对象的原始值

    */

    mutatingfunc fetch_sub(operand: RawType) -> RawType

    

    /**

     原子按位或操作

     

     - parameters:

        - operand: 按位或操作数

     

     - returns:按位或操作之前原子对象的原始值

    */

    mutatingfunc fetch_or(operand: RawType) -> RawType

    

    /**

     原子按位异或操作

     

     - parameters:

        - operand: 按位异或操作数

     

     - returns:按位异或操作之前原子对象的原始值

    */

    mutatingfunc fetch_xor(operand: RawType) -> RawType

    

    /**

     原子按位与操作

     

     - parameters:

        - operand: 按位与操作数

     

     - returns:按位与操作之前原子对象的原始值

    */

    mutatingfunc fetch_and(operand: RawType) -> RawType

}


/** 32位带符号整数原子类型 */

public struct AtomicInt:AtomicType {

    

    privatevar mAtomicValue = AtomicIntSwift()

    

    publictypealias RawType = Int32

    

    publicinit() {

        AtomicSwiftInit(&mAtomicValue,0)

    }

    

    publicinit(value: Int32) {

        AtomicSwiftInit(&mAtomicValue, value)

    }

    

    publicmutating func load() ->Int32 {

        returnAtomicSwiftLoad(&mAtomicValue)

    }

    

    publicmutating func store(by value:Int32) {

        AtomicSwiftStore(&mAtomicValue, value)

    }

    

    publicmutating func exchange(with value:Int32) -> Int32 {

        returnAtomicSwiftExchange(&mAtomicValue, value)

    }

    

    publicmutating func cas(expected:UnsafeMutablePointer<Int32>, desired:Int32) -> Bool {

        returnAtomicSwiftCAS(&mAtomicValue, expected, desired)

    }

    

    publicmutating func fetch_add(operand:Int32) -> Int32 {

        returnAtomicSwiftFetchAdd(&mAtomicValue, operand)

    }

    

    publicmutating func fetch_sub(operand:Int32) -> Int32 {

        returnAtomicSwiftFetchSub(&mAtomicValue, operand)

    }

    

    publicmutating func fetch_or(operand:Int32) -> Int32 {

        returnAtomicSwiftFetchOr(&mAtomicValue, operand)

    }

    

    publicmutating func fetch_xor(operand:Int32) -> Int32 {

        returnAtomicSwiftFetchXor(&mAtomicValue, operand)

    }

    

    publicmutating func fetch_and(operand:Int32) -> Int32 {

        returnAtomicSwiftFetchAnd(&mAtomicValue, operand)

    }

}


/** 布尔原子类型 */

public struct AtomicBool:AtomicType {

    

    privatevar mAtomicValue = AtomicBoolSwift()

    

    publictypealias RawType = Bool

    

    publicinit() {

        AtomicSwiftInit(&mAtomicValue,false)

    }

    

    publicinit(value: Bool) {

        AtomicSwiftInit(&mAtomicValue, value)

    }

    

    publicmutating func load() ->Bool {

        returnAtomicSwiftLoad(&mAtomicValue)

    }

    

    publicmutating func store(by value:Bool) {

        AtomicSwiftStore(&mAtomicValue, value)

    }

    

    publicmutating func exchange(with value:Bool) -> Bool {

        returnAtomicSwiftExchange(&mAtomicValue, value)

    }

    

    publicmutating func cas(expected:UnsafeMutablePointer<Bool>, desired:Bool) -> Bool {

        returnAtomicSwiftCAS(&mAtomicValue, expected, desired)

    }

    

    publicmutating func fetch_add(operand:Bool) -> Bool {

        assertionFailure("Atomic Bool does not support fetch operation!")

        returnfalse

    }

    

    publicmutating func fetch_sub(operand:Bool) -> Bool {

        assertionFailure("Atomic Bool does not support fetch operation!")

        returnfalse

    }

    

    publicmutating func fetch_or(operand:Bool) -> Bool {

        assertionFailure("Atomic Bool does not support fetch operation!")

        returnfalse

    }

    

    publicmutating func fetch_xor(operand:Bool) -> Bool {

        assertionFailure("Atomic Bool does not support fetch operation!")

        returnfalse

    }

    

    publicmutating func fetch_and(operand:Bool) -> Bool {

        assertionFailure("Atomic Bool does not support fetch operation!")

        returnfalse

    }

}


/** 64位无符号整数原子类型 */

public struct AtomicULong:AtomicType {

    

    privatevar mAtomicValue = AtomicULongSwift()

    

    publictypealias RawType = UInt64

    

    publicinit() {

        AtomicSwiftInit(&mAtomicValue,0)

    }

    

    publicinit(value: UInt64) {

        AtomicSwiftInit(&mAtomicValue, value)

    }

    

    publicmutating func load() ->UInt64 {

        returnAtomicSwiftLoad(&mAtomicValue)

    }

    

    publicmutating func store(by value:UInt64) {

        AtomicSwiftStore(&mAtomicValue, value)

    }

    

    publicmutating func exchange(with value:UInt64) -> UInt64 {

        returnAtomicSwiftExchange(&mAtomicValue, value)

    }

    

    publicmutating func cas(expected:UnsafeMutablePointer<UInt64>, desired:UInt64) -> Bool {

        returnAtomicSwiftCAS(&mAtomicValue, expected, desired)

    }

    

    publicmutating func fetch_add(operand:UInt64) -> UInt64 {

        returnAtomicSwiftFetchAdd(&mAtomicValue, operand)

    }

    

    publicmutating func fetch_sub(operand:UInt64) -> UInt64 {

        returnAtomicSwiftFetchSub(&mAtomicValue, operand)

    }

    

    publicmutating func fetch_or(operand:UInt64) -> UInt64 {

        returnAtomicSwiftFetchOr(&mAtomicValue, operand)

    }

    

    publicmutating func fetch_xor(operand:UInt64) -> UInt64 {

        returnAtomicSwiftFetchXor(&mAtomicValue, operand)

    }

    

    publicmutating func fetch_and(operand:UInt64) -> UInt64 {

        returnAtomicSwiftFetchAnd(&mAtomicValue, operand)

    }

}


然后我们可以对这些原子类型进行测试:

fileprivate func atomIntTest() {

    

    var atom =AtomicInt(value: 10)

    var value = atom.load()

    print("The initial atom value is:\(value)")

    atom.store(by: value +100)

    value = atom.load()

    print("Now, the atom value is:\(value)")

    

    var value2 = atom.exchange(with:-100)

    value = atom.load()

    print("Before exchange:\(value2), after exchange:\(value)")

    

    value = atom.load()

    value += 1 // 模拟被读取的值受外界破坏

    var bResult = atom.cas(expected: &value, desired:10)

    value = atom.load()

    print("cas result:\(bResult), value =\(value)")

    

    value = atom.load()

    bResult = atom.cas(expected: &value, desired:10)

    value = atom.load()

    print("cas result:\(bResult), new value:\(value)")

    

    value = atom.fetch_add(operand:5)

    value2 = atom.load()

    print("before add:\(value), after add:\(value2)")

    

    value = atom.fetch_sub(operand:5)

    value2 = atom.load()

    print("before sub:\(value), after sub:\(value2)")

}


fileprivate func atomBoolTest() {

    

    var atom =AtomicBool(value: true)

    var value = atom.load()

    print("The initial atom value is:\(value)")

    atom.store(by:false)

    value = atom.load()

    print("Now, the atom value is:\(value)")

    

    let value2 = atom.exchange(with:true)

    value = atom.load()

    print("Before exchange:\(value2), after exchange:\(value)")

    

    value = atom.load()

    value = !value // 模拟被读取的值受外界破坏

    var bResult = atom.cas(expected: &value, desired:false)

    value = atom.load()

    print("cas result:\(bResult), value =\(value)")

    

    value = atom.load()

    bResult = atom.cas(expected: &value, desired:false)

    value = atom.load()

    print("cas result:\(bResult), new value:\(value)")

    

    let _ = atom.fetch_add(operand:false)

}


fileprivate func atomULongTest() {

    

    var atom =AtomicULong(value: 10)

    var value = atom.load()

    print("The initial atom value is:\(value)")

    atom.store(by: value +100)

    value = atom.load()

    print("Now, the atom value is:\(value)")

    

    var value2 = atom.exchange(with:10000)

    value = atom.load()

    print("Before exchange:\(value2), after exchange:\(value)")

    

    value = atom.load()

    value += 1 // 模拟被读取的值受外界破坏

    var bResult = atom.cas(expected: &value, desired:10)

    value = atom.load()

    print("cas result:\(bResult), value =\(value)")

    

    value = atom.load()

    bResult = atom.cas(expected: &value, desired:10)

    value = atom.load()

    print("cas result:\(bResult), new value:\(value)")

    

    value = atom.fetch_add(operand:5)

    value2 = atom.load()

    print("before add:\(value), after add:\(value2)")

    

    value = atom.fetch_sub(operand:5)

    value2 = atom.load()

    print("before sub:\(value), after sub:\(value2)")

}


class ViewController: NSViewController {

    

    overridefunc viewDidLoad() {

        super.viewDidLoad()

                

        atomIntTest()

        atomULongTest()

        atomBoolTest()

    }

}


我们在执行最后一个atomBoolTest函数的时候会发生异常,由于原子布尔类型是不支持原子算术逻辑运算操作的,所以在实现中大家也能看到,我使用了assertionFailure函数来处理进入这些实现的方法中。

完整的工程代码可从此链接下载:http://download.csdn.net/detail/zenny_chen/9639566


  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值