V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
iOS 开发实用技术导航
NSHipster 中文版
http://nshipster.cn/
cocos2d 开源 2D 游戏引擎
http://www.cocos2d-iphone.org/
CocoaPods
http://cocoapods.org/
Google Analytics for Mobile 统计解决方案
http://code.google.com/mobile/analytics/
WWDC
https://developer.apple.com/wwdc/
Design Guides and Resources
https://developer.apple.com/design/
Transcripts of WWDC sessions
http://asciiwwdc.com
Cocoa with Love
http://cocoawithlove.com/
Cocoa Dev Central
http://cocoadevcentral.com/
NSHipster
http://nshipster.com/
Style Guides
Google Objective-C Style Guide
NYTimes Objective-C Style Guide
Useful Tools and Services
Charles Web Debugging Proxy
Smore
nellace
V2EX  ›  iDev

总感觉自己写的这个 block 怪怪的

  •  
  •   nellace · 2015-03-26 23:45:38 +08:00 · 3126 次点击
    这是一个创建于 3530 天前的主题,其中的信息可能已经有所发展或是发生改变。

    单例.h文件中
    - (void)getMatchesListWithHolder:(UIView *)holder
    Success:(void(^)(NSArray *dic))success;

    单例.m文件中
    - (void)getMatchesListWithHolder:(UIView *)holder Success:(void (^)(NSArray *))success
    {
    AFHTTPRequestOperationManager *manager =[AFHTTPRequestOperationManager manager];
    [manager GET:ApiUrl parameters:nil success:^(AFHTTPRequestOperation *operation, id responseObject) {
    if (responseObject) {
    NSArray *array =[[NSArray arrayWithObject:[responseObject objectForKey:@"matches"]]firstObject];
    success(array);
    NSLog(@"json:%@",array);
    }
    } failure:^(AFHTTPRequestOperation *operation, NSError *error) {
    NSLog(@"error:%@",error);
    }];
    }

    调用
    [[ApiDataManager instance]getMatchesListWithHolder:nil Success:^(NSArray *dic) {
    NSMutableArray *gameArray = [NSMutableArray arrayWithArray:dic];
    }];

    15 条回复    2015-03-31 22:38:41 +08:00
    yanke
        1
    yanke  
       2015-03-27 00:09:52 +08:00
    哥,能不能调整一下格式,看起累好累呀。
    derek80
        2
    derek80  
       2015-03-27 00:18:25 +08:00
    github gist
    nellace
        3
    nellace  
    OP
       2015-03-27 08:26:38 +08:00
    @yanke 本来要上图的,后来偷懒就直接copy过来了,代码什么的运行没问题,就是Success:(void(^)(NSArray *dic))success这一块自己都看糊涂了
    nellace
        4
    nellace  
    OP
       2015-03-27 08:27:32 +08:00
    @derek80 thx 还没用过gist,学一下待会
    likid
        5
    likid  
       2015-03-27 09:08:52 +08:00
    - (void)getMatchesListWithHolder:(UIView *)holder
    success:(void(^)(NSArray *dics))success;
    metrue
        6
    metrue  
       2015-03-27 10:01:12 +08:00
    v2ex是支持的 Markdown 的,调整格式看着舒服一点。
    特别是OC的代码,不然真是没有办法看啊。
    plutodai
        7
    plutodai  
       2015-03-27 12:46:38 +08:00
    没感觉有什么问题,期待大神的见解。不过加一个failure的block会不会更好一点
    nellace
        8
    nellace  
    OP
       2015-03-27 13:18:24 +08:00
    @plutodai 谢谢你读完了这段代码,我可能编辑的不带好看,好多大神都估计没看,运行起来没有问题,就是觉得怎么解释不通
    palxex
        9
    palxex  
       2015-03-27 13:59:58 +08:00
    ……你觉得哪里解释不通呢?我也看不出啥问题。
    vincentxue
        10
    vincentxue  
       2015-03-27 17:29:04 +08:00   ❤️ 2
    我个人属于代码洁癖型选手,个人挑一些小毛病,如下:

    1、方法名命名不规范,应该为 `- (void)getMatchesListWithHolder:(UIView *)holder success:(void(^)(NSArray *dic))success;` ,success 是小写。

    2、Block 参数变量名不规范。类型是 NSArray,变量名却写 `dic`。

    3、单例命名不规范,单例通常应该命名为 `sharedXXX`,例如 `[NSURLSession sharedSession]`。

    4、回调只有成功回调,没有失败的回调,如果请求失败了,那么回调就不会被执行。

    5、违反 MVC 设计模式。最好不要把 View 传进 Model,如果是要取 View 的参数就传这些参数,如果是要对 View 操作就在 Controller 的回调里操作。

    6、应该子类化 AFNetworking 为一个单例网络请求类,做一些必要的额外设置,提供 baseURL 以便于请求时只输入 URI 即可,而不同写完整的 URL。

    7、请求的 URI 地址命名没有含义,不利于识别。

    8、使用一句代码取层次较深的数据容易出错。并且应该使用字面量(这样做的好处请自行 Google)。

    9、没有对 `success` 回调做判断,如果调用者传入 nil,那么你调用 `success` 会造成 Crash。

    10、如果你的服务器使用 HTTP 错误码标识网络请求错误,那么 API 请求错误就肯定是使用 2XX 的状态码。而在 iOS 网络请求中 2XX 是表示成功的请求,那么此时你的 `responseObject` 是存在的,但是它是一个错误的数据,你简单的使用 if 判断这个对象是否存在来判断请求成功失败,这样做是有风险的。

    11、这个属于我个人的习惯,我认为方法的类型也应该是有区别的。类方法(+)应该是对整个模型层面的操作,实例方法(-)是对某单个模型的操作。例如有一个朋友圈类,发布朋友圈或者加载我的朋友圈应该是封装成类方法,对某一条朋友圈评论或赞应该封装成实例方法。又如有一个用户类,请求附近的用户,应该写成类方法,更新当前用户的资料,应该写成实例方法。如果按照我的这个逻辑,你的方法类型就不对了。


    我个人封装网络请求类似于这样:

    我自己的服务器不管是网络错误还是请求错误都不会返回 2XX 的状态码,所以我只要是进了成功的回调,那么这个请求一定是成功了。

    ```
    + (NSURLSessionDataTask *)getAuthCodeWithPhoneNumber:(NSString *)phoneNumber completionHandler:(OPTCompletionBlock)completionHandler {
    NSString *URLString = [kGetAuthCodeURI stringByAppendingPathComponent:phoneNumber];
    return [[OPTEngine sharedEngine] GET:URLString parameters:nil
    success:^(NSURLSessionDataTask *task, id responseObject) {
    !completionHandler ?: completionHandler(YES, nil);
    } failure:^(NSURLSessionDataTask *task, NSError *error) {
    !completionHandler ?: completionHandler(NO, [OPTError errorWithResponseError:error]);
    }];
    }
    ```

    ```
    typedef void (^OPTCompletionBlock)(BOOL success, NSError *error);
    ```

    另外回调也分为两种,一种是成功和失败分别回调,一种是成功和失败同一个回调,使用 BOOL 或者 NSError 标识请求是否成功,我个人偏向使用同一个回调,因为有时候需要在成功和失败时调用相同的代码(例如隐藏 HUD)。
    vincentxue
        11
    vincentxue  
       2015-03-27 17:31:59 +08:00   ❤️ 1
    nellace
        12
    nellace  
    OP
       2015-03-27 18:38:20 +08:00
    @vincentxue 先谢过你了,这么仔仔细细提出来每一条,真心感谢,我按着你这个规范去修改了
    tigerZhang
        13
    tigerZhang  
       2015-03-31 14:47:55 +08:00
    @vincentxue 请问你在github上是否有开源的项目,想看看你的代码,感觉可以从你代码里学到很多东西。
    vincentxue
        14
    vincentxue  
       2015-03-31 15:34:17 +08:00
    @tigerZhang

    过奖了,我目前没有可以开源的项目,主要都是做公司项目,私人项目都是涉及到自己服务器的,这部分不是很适合开源。我个人是个开源爱好者,但是可惜的是目前没有可以开源的代码。

    拥有开源项目也是我个人的愿望,但水平有限,不敢乱献丑。其实我个人水平很一般了,主要是题主发出来的这段代码写得确实是挺多小毛病的,显得我好像很厉害的样子。
    tigerZhang
        15
    tigerZhang  
       2015-03-31 22:38:41 +08:00
    @vincentxue 期待能看到你的开源项目
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   1995 人在线   最高记录 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 25ms · UTC 00:23 · PVG 08:23 · LAX 16:23 · JFK 19:23
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.