zoukankan      html  css  js  c++  java
  • 开发随笔(杂谈)

    1.支付问题

    (1)首先与支付宝签约,获取商户id和账号id   (2)下载相应的公钥私文件(加密签名的时候会用到) (3)下载支付宝sdk,看文档签约 获取公钥私钥  查看  调用支付接口  (4)生成订单信息  (5)调用支付宝客户端,由支付宝客户端跟支付宝安全服务器打交道 (6)返回支付结果给商户客户端和商户服务器 进行处理。

    2.开发流程

    首先先设定产品需求   分析进度影响进度的功能或者不能做的砍掉(有的安卓能做有的ios能做)  按照产品原型搭建界面,及时与美工沟通,有时候图片可能会有问题,还要与后台进行沟通 交流数据 开发中自己测试减少bug

    3.Block使用注意点(转载)

    1、在使用block前需要对block指针做判空处理。

    不判空直接使用,一旦指针为空直接产生崩溃。

    复制代码
    if (!self.isOnlyNet) {
        if (succBlock == NULL) { //后面使用block之前要先做判空处理
            return;
        }
        id data = [NSKeyedUnarchiver unarchiveObjectWithFile:[self favoriteFile]];
        if ([data isKindOfClass:[NSMutableArray class]]) {
            succBlock(data,YES);
        }else{
            succBlock(nil,YES);
        }
    }
    复制代码
    2、在MRC的编译环境下,block如果作为成员参数要copy一下将栈上的block拷贝到堆上(示例见下,原因参考

    3、在block使用之后要对,block指针做赋空值处理,如果是MRC的编译环境下,要先release掉block对象。

    block作为类对象的成员变量,使用block的人有可能用类对象参与block中的运算而产生循环引用。

    将block赋值为空,是解掉循环引用的重要方法。(不能只在dealloc里面做赋空值操作,这样已经产生的循环引用不会被破坏掉)

    复制代码
    typedef void(^SuccBlock)(id data);
    @interface NetworkClass {
        SuccessBlock _sucBlock;
    }
    @property (nonatomic,assign)BOOL propertyUseInCallBack;
    - (void) requestWithSucBlock: (SuccessBlock) callbackBlock;
    @end
     
    @implementation NetworkClass
    - (void) requestWithSucBlock: (SuccessBlock) callbackBlock {
        _sucBlock = callbackBlock;//MRC下:_sucBlock = [callbackBlock copy]; 不copy block会在栈上被回收。
    }
     
    - (void) netwrokDataBack: (id) data {
        if (data != nil && _sucBlock != NULL) {
            _sucBlock(data);
        }
        //MRC下:要先将[_sucBlock release];(之前copy过)
        _sucBlock = nil; //Importent: 在使用之后将Block赋空值,解引用 !!!
    }
    @end
     
    //=======================以下是使用方===========================
    @implementation UserCode
    - (void) temporaryNetworkCall
    {
        NetworkClass *netObj = [[NetworkClass alloc] init];
        netObj.propertyUseInCallBack = NO;
        [netObj requestWithSucBlock: ^(id data) {
            //由于block里面引用netObj的指针所以这里产生了循环引用,且由于这个block是作为参数传入对象的,编译器不会报错。
            //因此,NetworkClass使用完block之后一定要将作为成员变量的block赋空值。
            if (netObj.propertyUseInCallBack == YES) {
                //Do Something...
            }
        }];
    }
    @end
    复制代码

    还有一种改法,在block接口设计时,将可能需要的变量作为形参传到block中,从设计上解决循环引用的问题。

    如果上面Network类设计成这个样子:

    复制代码
    @class NetowrkClass;
    typedef void(^SuccBlock)(NetworkClass *aNetworkObj, id data);
    @interface NetworkClass
    //...
    @end
    @implementation NetworkClass
    @end
     
    @implementation UserCode
    - (void) temporaryNetworkCall
    {
        NetworkClass *netObj = [[NetworkClass alloc] init];
        netObj.propertyUseInCallBack = NO;
        [netObj requestWithSucBlock: ^(NetworkClass *aNetworkObj, id data) {
            //这里参数中已经有netObj的对象了,使用者不用再从block外引用指针了。
            if (aNetworkObj.propertyUseInCallBack == YES) {
                //Do Something...
            }
        }];
    }
    @end
    复制代码

    4、使用方将self或成员变量加入block之前要先将self变为__weak

    5、在多线程环境下(block中的weakSelf有可能被析构的情况下),需要先将self转为strong指针,避免在运行到某个关键步骤时self对象被析构。

    第四、第五条合起来有个名词叫weak–strong dance,来自于2011 WWDC Session #322 (Objective-C Advancements in Depth)

    以下代码来自AFNetworking,堪称使用weak–strong dance的经典。

    复制代码
    __weak __typeof(self)weakSelf = self;
    AFNetworkReachabilityStatusBlock callback = ^(AFNetworkReachabilityStatus status) {
        __strong __typeof(weakSelf)strongSelf = weakSelf;
        strongSelf.networkReachabilityStatus = status;
        if (strongSelf.networkReachabilityStatusBlock) {
            strongSelf.networkReachabilityStatusBlock(status);
        }
    };
    复制代码
    Review一下上面这段代码,里面玄机不少。

    第一行:__weak __typeof(self)weakSelf = self;

    如之前第四条所说,为防止callback内部对self强引用,weak一下。

    其中用到了__typeof(self),这里涉及几个知识点:

    a. __typeof、__typeof__、typeof的区别

    恩~~他们没有区别,但是这牵扯一段往事,在早期C语言中没有typeof这个关键字,__typeof、__typeof__是在C语言的扩展关键字的时候出现的。

    typeof是现代GNU C++的关键字,从Objective-C的根源说,他其实来自于C语言,所以AFNetworking使用了继承自C的关键字。

    b.对于老的LLVM编译器上面这句话会编译报错,所以在很早的ARC使用者中流行__typeof(&*self)这种写法,原因如下

    大致说法是老LLVM编译器会将__typeof转义为 XXX类名 *const __strong的__strong和前面的__weak关键字对指针的修饰又冲突了,所以加上&*对指针的修饰。

    第三行:__strong __typeof(weakSelf)strongSelf = weakSelf;

    按照之前第五条的说法给转回strong了,这里__typeof()里面写的是weakSelf,里面写self也没有问题,因为typeof是编译时确定变量类型,所以这里写self 不会被循环引用。

    第四、五、六行,如果不转成strongSelf而使用weakSelf,后面几句话中,有可能在第四句执行之后self的对象可能被析构掉,然后后面的StausBlock没有执行,导致逻辑错误。

    最后第五行,使用前对block判空。

  • 相关阅读:
    win10 uwp 弹起键盘不隐藏界面元素
    win10 uwp 存放网络图片到本地
    win10 uwp 存放网络图片到本地
    sublime Text 正则替换
    sublime Text 正则替换
    win10 uwp 绘图 Line 控件使用
    win10 uwp 绘图 Line 控件使用
    AJAX 是什么?
    什么是 PHP SimpleXML?
    PHP XML DOM:DOM 是什么?
  • 原文地址:https://www.cnblogs.com/liuyang666/p/5281878.html
Copyright © 2011-2022 走看看