iOS开发-记录下在开发过程中遇到的问题的解决方案及经验总结-1

声明:本文以下内容均摘自笔者从初学阶段至今的日常笔记,仅供学习交流参考,难免有些理解偏差,欢迎指出

1.badgeVaule气泡提示,self.navigationController.tabBarItem.badgeValue

2.git终端命令方法> pwd查看全部 >cd>ls >之后桌面找到文件夹内容,以cd xxxx ,ls格式>git status查看>git pull origin master从网上储存库中下下来。 返回上一级地址命令cd ..

3.全球最大开源代码托管平台——SourceForge

4.sections更改数量可使tableview分量

5.static cells静态tableview

6.nothing to commit, working directory clean 表示上传Git成功

7.git提交步骤

  • git add . //此处add后加空格.

  • git commit -m "xxx"

  • git pull origin master //更新代码

  • git push origin master //提交

8.Identifier是写在navigation上边的

9.AF的方法中全部属于异步下载。

10.无论使用collectionView还是tableView的自定义cell,都需要先在viewDidLoad中注册cell

11.可以使用mac自带的数码测色计来获取颜色的RGB值

12.例子:
indexPath.row==0 && indexPath.section==1
不同的section中的indexpath的row是会归0重置的,从0开始重头计

13.代理协议写在m文件即可,不用过多的暴露在头文件中

14.radioButton的图片更改方法,不用代码实现,在button的State 。cc。oo。nn。ff。ll。gg。中选择Default为未点击时状态,可赋予图片,选择selected为选中时状态,可赋予图片,直接使用imageView的方法是不专业的

15.在button的中选择Default为未点击时状态,,直接使用imageView的方法是不专业的。

16.textView加边框

#import <QuartzCore/QuartzCore.h>    
textview对象.layer.borderColor = UIColor.grayColor.CGColor;
textview对象.layer.borderWidth = 5;
self.textView.layer.masksToBounds = YES;
self.textView.layer.cornerRadius = 5;

17.ruby -e "$(curl -fsSL https://raw.githubusercontent...)" //下载安装git插件

18.scrollView可以专门用来自动处理键盘布局,但需要嵌入代码

19.有造好的轮子就要用,不要傻乎乎的想要自己去造,理解就可以了,闲暇时间自己研究,工作当中效率进度第一

20.alloc之后几乎全是init方法

21. if(indexPath.row==2 && indexPath.section==0){//row表示在一个section下顺序第几个,section表示第几个section

22.区别:

-(void)viewDidLoad//加载后调用
-(id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil//进入后就调用

23.git比svn要强大

24.@property (assign,nonatomic) BOOL hONG; //bool型只能用于状态判断,只有yes和no,非黑即白 assign表示弱类型的赋值 nonatomic会有先后顺序 简单变量是assign,指针变量是strong
//@property的意思是属性,类似于c++的一个成员变量,在oc中成为一个类的属性
@implementation具体方法的实现

25.来记个方法,这是针对不同类型的初始化方法

//push界面之前的初始化方法,该方法是在push  xib类型界面之前进行初始化的方法
LSIntegralShopViewController * integrelShopViewController =[[LSIntegralShopViewController alloc]initWithNibName:@"LSIntegralShopViewController" bundle:nil];  //这里那个nibName是写的那个controller的对应的那个类

//针对toryboard的初始化方法
[WPUtil getViewControllerWithIdentifier: storyboardName:]  //此处Identifier是storyboard上的Identifier ID,而UINavigationController * homeNavigationController = [WPUtil getViewControllerWithIdentifier:@"homeNavigation" storyboardName:@"Home"];这里的Identifier则是Navigation上的ID,注意区分

26.上下bar的地方切图使用时,后缀加上@2x,注意是在.png前使用,同时图盘拖到2x那格中

27.2x图片清晰度更高

28.已经在界面上都配置好了,代码里面就不需要这些设置了
只需处理点击事件,比如选中第一个,第一个button.selected = YES,其他两个button.selected = NO

29.UIButton的edge可以调整image和title

30.[self.view endEditing:YES]; //直接撤销键盘的方法

31.manager.responseSerializer.acceptableContentTypes = [NSSet setWithObjects:@"text/html", nil];//默认为json格式,若为json可省略这行代码

32.+方法写在头文件中,谁都可以调用,只要引用其头文件名称,如viewController是可以在任何地方初始化任意次的

33.使用最底部或最上部的UIButton或某个控件来支撑住scrollview,来让scrollview知晓其最大距离

34.NSUInteger表示无符号整型,即非负数

35.严格按照流程来,先在外边,比如说美工发给你的图片,把名字改好,xxx@2x.png,然后再拖进去,还有,文件名不要出现空格,这些有空格的通通改掉,把有问题的全部删了,重新加

36.至于重写set和get方法,简要说明一下,当我们使用@property这用法之后,系统便会自动给我们定义的变量以一个默认的set和get方法。插一句,_any和self.any的区别,_any就是只指_any本身,是系统会生成的,而如果我们重写了any的set方法后,self.any会调用我们重写的set方法中的内容,而_any不是,比如这句

-(void)setCount:(NSUInteger)count
{
    _count = count;
}

这里表示的是将系统默认给我们生成的count变成我们自定义的count,达到我们想要的目的。_any就是单单指当我们使用@property后系统给我自动生成的一个any,而self.any不同,它会自动调用(set和get方法本身就包含在其中,也可以理解为就是它自身的一个属性一部分)我们重写后的set方法,当我们self.any的时候,其中重写的set方法中的任何内容都会被我们使用,所以即使我们只self.any,也可实现许多只要set方法中写出的效果,大致是这个意思

37.推荐使用代理传值,通知的观察者模式效率低下

38.cell控制视图显示,controller负责网络解析

39.取数据的时候,要看返回的数据是什么样子的,需要两个就两个,需要一个就一个

data =     {
    CurrentPageIndex = 1;
    PageSize = 10;
    TotalItemCount = 1;
    TotalPageCount = 1;
    data =         (
                    {
            ClickNumber = 0;
            ID = 1796;
            Norm = "\U6876";
            Picture = "/upload/goods/default.jpg";
            SellerRetailPrice = 10;
            TheSorting = 12500000;
            TypeID = 22;
            goodsName = "\U51b0\U51b0\U4e50";
            goodsTypeName = "\U7eaf\U51c0\U6c34";
            sellerId = 125;
            sellerName = "\U51e4\U51f0\U57ce\U6c34\U5e97";
            sellerState = 1;
        }
    );
};
    msg = "<null>";
    result = ok;
}

第一个data取的是里面的一大堆即一个字典,第二个data才是个数组,@"data"这个大体是指前一个data是拿到一个字典的数据,第二个data是那里面的数组咯

40.不要直接用button或控件push到下一个界面,尤其是在tableView的cell上

41.shopTVC.delegate = self;//上一个界面的代理设为这个界面自身,在上一个见面中调用代理的时候,因为上一个界面的代理已经被设置为这个界面,所以在上一个见面中调用其自身代理时,实际上是这个界面在执行

42.没有了summary,但是原来的summary的功能可以在targets的general里面找到

43.关于尝试新方法,比如:将字典中的值赋值给一个float,有时候.不行可以换( ) 或 ]试试看有没有其方法

float left= [aaa[@"abc"] floatValue];

44.else if (self.btnOfAddress.selected){ //点了之后立马又弹回去了,当执行的时候按钮状态已经弹回去了,如果需要一直是点击状态那么你需要设置selected=YES,这是状态是需要设置的,不然就不会有效果,需要是选中状态,那么你就要在合适的位置设置起,btn.selected = YES

45.总之,要看他数据需要什么,保存的是哪里

46.本着,谁分配谁管理的原则

47.thread:breakpoint 1.2,在该行最左侧的蓝色矩形区域右键,选择delete breakpoint即可。

48.逻辑步骤关系,所有异步都要先完成数据的请求,成功后,返回数据信息后才开始跳转界面,换句话说,需要将需要提交的数据全部获取到之后,再做统一提交处理

49.所有网络请求都用异步,上传提交也叫下载,只不过下载的内容可能就是个提示性的东西,提示你提交成功没有

50.字符串比较用isEqualToString,不用等号, ]是调方法 ( )是优先级

51.提交输入框信息,需要在解析数据时获取,而不能在初始化时就去获取

52.断点不是只能在运行前设置,在运行当中也可以设置

53.一切都以数据为中心,先拿到数据,再显示页面。比如tableView是先得到返回行数,再执行的cell显示,白话讲就是,点击了左边的cell选中后,开始解析,由于在解析时保存了数据,这样返回行就有了数据,这时就会返回显示返回行数目的数据,这样一来便可以在cell中显示

54.异步下载中间的代码是异步的,要执行,但是不是马上执行,网络有数据返回的时候

55.然而机智如我,合理运用函数参数名赋予的作用

-(void)setSelected:(BOOL)selected animated:(BOOL)animated {
    [super setSelected:selected animated:animated];//这个函数是当cell被点击的时候调用的方法,最好不要用作初始化的地方
    if(selected == YES){
        self.buttonOfDetailed.hidden=NO;
    }else{
        self.buttonOfDetailed.hidden=YES;
    }

    // Configure the view for the selected state
}

56.tableView的cell重复相应点击的问题可能是在Table View这一栏选项中关于Selection的选择问题,一般单次响应点击会选择Single Selection这一选项

57.这个方法只有在手指点击cell,然后离开后才调用,而不是点击的时候就调用

-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath;

58.tableView果然是用到最多最多的,无处不在,以各种各样你想象不到的方式出现,给你一种似乎任何效果都可以用它来实现出来的内心的震撼

59.command+3(2,1)调节模拟器放大尺寸

60.swift注意:如果你的代码中有不需要改变的值,请使用let关键字将它声明为常量。只将需要改变的值声明为变量。

61.swift中,常量的值一旦设定就不能改变,而变量的值可以随意更改。常量和变量必须在使用前声明,用let来声明常量,用var来声明变量。
常量和变量必须在使用前声明,用let来声明常量,用var来声明变量。下面的例子展示了如何用常量和变量来记录用户尝试登录的次数:

let maximumNumberOfLoginAttempts = 10
var currentLoginAttempt = 0

这两行代码可以被理解为:

“声明一个名字是maximumNumberOfLoginAttempts的新常量,并给它一个值10。然后,声明一个名字是currentLoginAttempt的变量并将它的值初始化为0.”

在这个例子中,允许的最大尝试登录次数被声明为一个常量,因为这个值不会改变。当前尝试登录次数被声明为一个变量,因为每次尝试登录失败的时候都需要增加这个值。

你可以在一行中声明多个常量或者多个变量,用逗号隔开:

var x = 0.0, y = 0.0, z = 0.0

62.initWithNibName是加载View视图事件

63.关于界面适配的问题,一个是对于底部tabbar所留下的空白的处理方法:

//隐藏底部tabbar留下的空白
self.hidesBottomBarWhenPushed = YES;

这里http://www.cocoachina.com/bbs... 有一个思路的参照
但是具体实现需要具体分析一下,总的来说是把该方法加到即将要进入(即存在多余tabbar空白的界面)的前一个界面的-(void)viewWillAppear:(BOOL)animated中来实现,也就是在页面跳转前

64.思路思路思路啊

#pragma mark - 发表帖子
-(void)publishAction
{
    //判断是否已经登陆
    BOOL isLogin = [Utility getBoolForKey:GYH_PATIENT_IS_LOGIN];
    if (isLogin) {
        //进入发帖界面
        UIViewController *vc = viewControllerInStoryBoard(@"GHYNewPostController", @"1_home_7_quan");
        [self.navigationController pushViewController:vc animated:YES];
    }else{
        //调出登陆界面,登陆界面的返回是直接返回上一级界面,并不是主页
        [Utility jumpToLoginWithViewController:self];
    }

}

65.确实是深深感到对代码的层次深度的理解到了瓶颈期的时候。

66.本着别人坑我,我不坑人的态度,变量的命名和注释都是极尽规范和详细的,也算对的起一个处女座的人设了。

67.for in实际上是快速枚举,跟for循环意义上还是有区别的。目前可以理解为for...in 语句用于对数组或者对象的属性进行循环操作

68.NSArray的枚举操作中有一条需要注意:对于可变数组进行枚举操作时,你不能通过添加或删除对象这类操作来改变数组容器。如果你这么做了,枚举器会很困惑,而你将得到未定义的结果。

69.git经过一次更改就要提交一次是为了给自己一个后悔的机会,如果做了20次更改的时候一起提交,那么想要重新返回之前的某一项功能就会十分的费时费力,得不偿失

70.UITableViewCell的属性selectionStyle设置为UITableViewCellSelectionStyleNone 如果是在storyboard里面,就设置为none类型 //关于cell的点击响应不显示颜色,即达到点击无效果

71.当手指离开某行时,就让某行的选中状态消失

-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{
    //当手指离开某行时,就让某行的选中状态消失
    [tableView deselectRowAtIndexPath:indexPath animated:YES];
    self.tableView.backgroundColor = [UIColor clearColor];

    if(indexPath.section == 0 && indexPath.row == 2){
    
    }
}

72.图片圆形

_btnHead.layer.masksToBounds = YES; _btnHead.layer.cornerRadius = 按钮宽的一半;  //图片圆形

73.记一笔,关于tableView的section的header,是一个之前注意到的地方,今天突然重新意识到的问题,这个header如果什么都不填写会显示为no header,就是取消header的显示状态,那么,我们可以用一个空格代替的方式来达到既不想有文字展示但是又有header显示的效果。

74.思路要清晰,要灵活,困的时候不要写代码,越写越乱,困了直接去睡觉

75.要隐藏section下的cell的话,在返回section个数的地方进行相应判断即可

76.如何改变section的headr的颜色

-(UIView *) tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section 
{  
    UIView *headerView = [[[UIView alloc] initWithFrame:CGRectMake(0, 0, tableView.bounds.size.width, 30)] autorelease];  
    if (section == integerRepresentingYourSectionOfInterest){                                  
        [headerView setBackgroundColor:[UIColor redColor]];  
    }else {    
        [headerView setBackgroundColor:[UIColor clearColor]];  
    }
    return headerView;
}

77.如果在视图上固定了cell的行高,就不需要在代码中重复设定

78.如果实在找不到或不确定在哪里使用过某个值,去放大镜哪里搜索看看吧。

79.虽然感觉遇到的都是小的功能问题,但都是重要的逻辑性问题。

80.在做网络请求提交的时候,如果涉及到用户个人的信息,一定要有能够识别是哪一个用户的信息在里面,否则会出现问题,找不到具体是哪个用户的信息

81.alertView的内容最好分开写,放在一起写可能会出现调用延迟的情况

82.UIAlertView的响应方法要想被执行,那么UIAlertView的delegate必须是设为self。

83.不是万不得已,不要写死数据和模块

84.字符串NSString中去掉空格

NSString * string =[str3 stringByReplacingOccurrencesOfString:@";" withString:@" "];//OS字符串NSString中去掉空格(或替换为某个字符串)

85.设置异步解析断点时,要在方法内设置断点,因为代码执行不是同步进行的,不会一步一步按照顺序执行下去,所以如果不是在方法内部设置断点,可能会出现直接跳过这段方法而查看不到的断点行为。

86.字典NSDictionary一般的遍历方法都是:

NSArray* arr = [yourdictonary allKeys];for(NSString* str in arr){
    NSLog("%@", [yourdictonary objectForKey:str]);
}

但是如果就这样遍历的话,所打印出来的结果是不按照你添加的顺序打印出来的。很简单,只要先将arr进行排序,再将字典遍历打印出来:

NSArray* arr = [yourdictonary allKeys];arr = [arr sortedArrayUsingComparator:^NSComparisonResult(idobj1, id obj2)
{
    NSComparisonResult result = [obj1 compare:obj2];
    return result==NSOrderedDescending;
}];

就这样,将字典的key进行一个排序后,就能根据自己的需求将字典遍历打印出来。

87.在mac上浏览图片不需要双击,选中后直接按空格就可以了

88.改变字符串中个别字符的颜色:
NSString * onlineString = @"";

if (isOnline == 1) {
    onlineString = @"[在线]";
}else{
    onlineString = @"[离线]";
}
NSString * name = [NSString stringWithFormat:@"%@%@",onlineString, cell.nameLabel.text];
NSMutableAttributedString * attString = [[NSMutableAttributedString alloc] initWithString:name];
[attString addAttributes:@{NSForegroundColorAttributeName:[UIColor lightGrayColor], NSFontAttributeName:MyFont(13)} range:[name rangeOfString:onlineString]];
cell.nameLabel.attributedText = attString;

//设置text字的属性,比如说同一个label中的不同字符串可以拥有不同的属性,首先初始化,NSForegroundColorAttributeName,设置字体颜色,NSFontAttributeName,字体大小,range,范围,name rangeOfString:onlineString]],name中的onlineString。最后显示的时候就不用text属性,而用attributedText属性

89.关于IOS系统升级后的屏幕适配的一个原因:
这个原因确实是LaunchImage没配。不过这么说确实容易觉得奇怪,这又不是启动界面,直觉这俩好像没什么关系。所以我来讲个故事……

很久以前,iPhone就是这么矮矮的。

后来有一天,出来了iPhone5,宽度不变,高度长了一截。记得大家当时都在吐槽……

无论如何,当时 AppStore 已经有很多的app了;屏幕变了以后,原来的那些app该怎么显示呢?肯定不能直接拉长,把方块拉成长方形;也不能直接按拉长的屏幕尺寸渲染,虽然理论上不应该有问题,但当时有app的代码是写死坐标+计算相结合的,直接改变肯定会造成显示错乱。

所以苹果想的办法就是,给原来的app一点准备的时间,要求尽快适配新屏幕;在适配好之前,显示的高度不变,像你看到的那样居中显示,上下各一道黑边;适配好之后,再按拉长的屏幕显示。

那么app怎么告诉苹果系统,对于这划时代的新屏幕它是准备好了还是没准备好呢?答案就是:LaunchImage。

系统会先看一个app有没有4寸的LaunchImage。只要给了,那就假定已经适配好了,会按4寸显示;反之,只要没给,就会按3.5寸显示,也就是你看到的黑边。

从那以后,再推出iPhone6、6Plus的时候,也是按同样的方法区分的。没给3x LaunchImage的会直接拉伸显示,给了的才会按大屏渲染,帮助已有的app度过那青黄不接的年代。

90.界面延迟跳转

[self performSelector:@selector(jumpToModifyInfo) withObject:nil afterDelay:2.0];  //界面延迟跳转

91.

-(void)generateSelectedIndexPath
{

    if (![MyUtil isNilOrEmpty:self.attentionTopic]) {
        NSArray * array = [self.attentionTopic componentsSeparatedByString:@";"];
        for (NSInteger i = 0; i < array.count; i++) {
            NSString * oneTopic = array;
            for (NSInteger j = 0; j < self.categories.count; j++) {
                NSString * typeName = self.categories[j][@"mentalType"][@"type_name"];
                if ([oneTopic isEqualToString:typeName]) {
                    [self.categoryChooseStates replaceObjectAtIndex:j withObject:@(YES)];
                }
            }
        }
    }
}

//这个方法是个实际遇到的问题,首先讲获取到的字符串利用字符串的分割而转换为数组,这样做的一个目的是可以去到这个数组的count,之后进行一次小于数组长度的循环,NSString oneTopic = array;是指每循环一次都将数组内的第i个字符串赋给oneTopic,然后在进行一次针对self.categories的循环,self.categories中保存着全部的“感情话题”的数据,是一个字典,这个循环的目的就是用数组中的oneTopic去字典self.categories中遍历寻找相同的字符串,NSString typeName = self.categoriesj[@"type_name"];这句话也是将字典self.categories中@"mentalType"的内容保存在这个字符串里,并在这里if ([oneTopic isEqualToString:typeName])进行对照和判断。如果在字典中找到相同的字符串,那么[self.categoryChooseStates replaceObjectAtIndex:j withObject:@(YES)]; 这句话就是说,根据字符串相同时所对应的index也就是这个j的值(j也可以理解为是第几个字符串),来改变bool的状态(默认为No),当Bool为yes是,会再其他方法中改变cell的显示状态

92.

STopicViewController * vc = [[UIStoryboard storyboardWithName:@"SSTopicCollectionVC" bundle:nil] instantiateViewControllerWithIdentifier:@"sss"];
//把当前界面的self.attentionTopic的值,直接传给下一个界面的attentionTopic
vc.attentionTopic = self.attentionTopic;
[self.navigationController pushViewController:vc animated:NO];

//关于界面传值这个东西,也不是说逻辑上的理解,总之就是头脑要清醒,要想清楚是怎么传,怎么得到。上面这个方法就是A类中的全局变量self.attentionTopic的值传给B类中的全局变量attentionTopic来使用,利用

STopicViewController * vc = [[UIStoryboard storyboardWithName:@"SSTopicCollectionVC" bundle:nil] instantiateViewControllerWithIdentifier:@"sss"];

这个方法来拿到B类的实例,也就是获取到B类,这样就可以获取到B类中h文件中声明的变量,利用A类的变量来直接赋值给B类的变量,直接改变在B类中attentionTopic的值,以此来达到见面之间传值的目的。ps:A类视图跳转到B类视图

93.
//保存选中时的数据

-(NSString *)getMentalType
{
    NSMutableArray * tmpArray = [@[] mutableCopy];
    for (NSInteger i = 0; i < self.categoryChooseStates.count; i++) {
        BOOL isChoose = [self.categoryChooseStates boolValue];
        if (isChoose) {
            [tmpArray addObject:self.categories[@"mentalType"][@"type_name"]];
        }
    }
    if (tmpArray.count == 0) {
        return @"";
    }
    NSString * string = [tmpArray componentsJoinedByString:@";"];
    return string;
}

//相当于整个方法就是调用最后这个返回的string 

94.网络解析更换借口地址后,参数记得同时调整

95.传值要在界面跳转之前完成,先有数据,后有显示

96.取到cell的index

-(void)tapComplaintBtn:(SSmyReferCell *)cell
{
    NSIndexPath * indexPath = [self.tableView indexPathForCell:cell];
    SSComplainViewController * vc = [[UIStoryboard storyboardWithName:@"MyCenter" bundle:nil]instantiateViewControllerWithIdentifier:@"complain"];
    vc.bIdStr = self.myQuestionList[indexPath.section][@"question"][@"id"];
    [self.navigationController pushViewController:vc animated:YES];

}

//取到cell的index

97.label设置边框

//label设置边框

CALayer * layer = [self.classLabel layer];
[layer setCornerRadius:10];
[layer setMasksToBounds:YES];
layer.borderColor = [[UIColor lightGrayColor] CGColor];
[layer setBorderWidth:1];
[self.view addSubview:self.classLabel];

98.调用方法时,要遵循代理协议
textView.delegate = self;设置好委托。就能响应
-(void)textViewDidBeginEditing:(UITextView *)textView方法
-(void)textViewDidEndEditing:(UITextView *)textView方法了 

99.text居中显示

cell textLabel textAlignment = UITextAlignmentCenter  //cell.label的text居中显示

100.关于Label显示不完过长字符串的问题,在视图右边调整行数,以及右上的宽度,outLaout不要约束宽度

101.在强调一遍,界面传值时,A传值给B,现在B界面的头文件中声明好用来保存的参数,然后,在A界面实例化B的类名,然后objectB.用于保存的参数=A的self.传值的参数

102.调用A类方法时,注意在B类头文件中声明想要引用的对应的方法名

103.想要拿到具体数据时,接口解析后返回的参数要看清楚字段的数量和名称
如:

(lldb) po responseObject[@"data"]
{
    code = 0;
    complaint =     {
        "b_id" = 889;
        "b_type" = 1;
        content = Tyyygggghhjgffddcvvbb;
        "create_time" = "2015-10-19 00:39:16";
        id = 19;
        "reason_id" = 2;
        state = 0;
    };
    msg = "\U64cd\U4f5c\U6210\U529f";
}

就应该以responseObject@"data"[@"state"]的形式来调用

104.解析到参数内容是整数的,需要进行比较时,如下处理:

NSInteger state = [responseObject[@"data"][@"complaint"][@"state"] integerValue];
if(state == 1){
    self.handleState.text = @"客服已处理";
}else{
    self.handleState.text = @"处理中";
}

105.swift用let来声明常量,用var来声明变量。常量与变量名不能包含数学符号,箭头,保留的(或者非法的)Unicode 码位,连线与制表符。也不能以数字开头,但是可以在常量与变量名的其他地方包含数字。

106.swift你可以更改现有的变量值为其他同类型的值,如:friendlyWelcome的值从"Hello!"改为了"Bonjour!"。与变量不同,常量的值一旦被确定就不能更改了。尝试这样做会导致编译时报错.

107.swift你可以用println函数来输出当前常量或变量的值,println是一个用来输出的全局函数,输出的内容会在最后换行。如果你用 Xcode,println将会输出内容到“console”面板上。(另一种函数叫print,唯一区别是在输出内容最后不会换行。)

108.swift与 Cocoa 里的NSLog函数类似的是,println函数可以输出更复杂的信息。这些信息可以包含当前常量和变量的值。

Swift 用字符串插值(string interpolation)的方式把常量名或者变量名当做占位符加入到长字符串中,Swift 会用当前常量或变量的值替换这些占位符。将常量或变量名放入圆括号中,并在开括号前使用反斜杠将其转义:

println("The current value of friendlyWelcome is (friendlyWelcome)")
// 输出 "The current value of friendlyWelcome is Bonjour!
//意思就是输出printIn内参数的值或内容
object-c中的写法就是 Dlog(@"The current value of friendlyWelcome is %@",friendlyWelcome);
就是这点区别

109.如果在上一个if中进行了bool型判断,那么为了避免列表上下滑拉刷新时所造成的显示混乱,那么就要在下面的else中写入相反的bool量,即代码的重用问题

110.与其他大部分编程语言不同,Swift 并不强制要求你在每条语句的结尾处使用分号(;),当然,你也可以按照你自己的习惯添加分号。有一种情况下必须要用分号,即你打算在同一行内写多条独立的语句:

let cat = "?"; println(cat)
// 输出 "?"

110.swift你可以访问不同整数类型的min和max属性来获取对应类型的最大值和最小值:

let minValue = UInt8.min  // minValue 为 0,是 UInt8 类型的最小值
let maxValue = UInt8.max  // maxValue 为 255,是 UInt8 类型的最大值

111.Double表示64位浮点数。当你需要存储很大或者很高精度的浮点数时请使用此类型。

Float表示32位浮点数。精度要求不高的话可以使用此类型。
注意:
Double精确度很高,至少有15位数字,而Float最少只有6位数字。选择哪个类型取决于你的代码需要处理的值的范围。

112.Swift 是一个类型安全(type safe)的语言。类型安全的语言可以让你清楚地知道代码要处理的值的类型。如果你的代码需要一个String,你绝对不可能不小心传进去一个Int。

113.当推断浮点数的类型时,Swift 总是会选择Double而不是Float。
如果表达式中同时出现了整数和浮点数,会被推断为Double类型

114.不同整数类型的变量和常量可以存储不同范围的数字。Int8类型的常量或者变量可以存储的数字范围是-128~127,而UInt8类型的常量或者变量能存储的数字范围是0~255。如果数字超出了常量或者变量可存储的范围,编译的时候会报错:

let cannotBeNegative: UInt8 = -1
// UInt8 类型不能存储负数,所以会报错
let tooBig: Int8 = Int8.max + 1
// Int8 类型不能存储超过最大值的数,所以会报错

115.Swift 有两个布尔常量,true和false:

let orangesAreOrange = true
let turnipsAreDelicious = false

116.如果你在需要使用Bool类型的地方使用了非布尔值,Swift 的类型安全机制会报错。下面的例子会报告一个编译时错误:

let i = 1
if i {
    // 这个例子不会通过编译,会报错
}

然而,下面的例子是合法的:

let i = 1
if i == 1 {
    // 这个例子会编译成功
}

i == 1的比较结果是Bool类型,所以第二个例子可以通过类型检查。类似i == 1这样的比较,请参考基本操作符。

和 Swift 中的其他类型安全的例子一样,这个方法可以避免错误并保证这块代码的意图总是清晰的。

117.shift+command+k 开关模拟器键盘

118.关于判断tableView上拉下滑移动的一个思路:

-(void)scrollViewDidScroll:(UIScrollView *)scrollView{

    if (scrollView.contentOffset.y > _oldOffset) {//如果当前位移大于缓存位移,说明scrollView向上滑动

    }

    _oldOffset = scrollView.contentOffset.y;//将当前位移变成缓存位移
}

//就是声明一个变量_oldOffset,初始化为0,因为创建tableView时偏移量为0。然后把每次偏移后的值赋值给_oldOffset,下一次的时候跟上一次比较就能判断是上移还是下移了
-(void)scrollViewWillBeginDragging:(UIScrollView *)scrollView {
    oldY = scrollView.contentOffset.y;
}

-(void)scrollViewDidEndDragging:(UIScrollView *)scrollView willDecelerate:(BOOL)decelerate {
   if( scrollView.contentOffset.y > oldY) {
      //向下
    }else//向上
    }

}

//这样也可以

119.可以在storyBoard的右边Class Prefix处设立类的前缀,统一类名格式

120.如何去除tableView顶端的空白
在包含这个tableview的controll里面添加:

self.automaticallyAdjustsScrollViewInsets = NO;

解决。

121.想要透明的话就直接设置navigationbar透明,而不是颜色透明,在navigationbar上面再加个view,就可以对view的颜色设置clearcolor,这是个取巧的方法,挺不错的。

如果navigationbar出现黑色是因为一开始我的这个controllerVIew在navigationbar那个位置上没有东西,也就是覆盖到navigationbar上面的view颜色是空,而window的颜色也是空的,所以造成了出现黑色的情况 ,解决方法:把tableView拖拽至顶部,让navigationbar的底下有内容即可。

就是和他们说的不能把window的backgroundColor设为透明色一样,因为window是最底层了,再透明就没东西了。

window的backgroundColor可以设为透明色,但是结果就是黑色。

122.去掉navigationbar下面的黑色边线

//去掉navigationbar下面的黑色边线
[[UINavigationBar appearance] setBackgroundImage:[[UIImage alloc] init] forBarPosition:UIBarPositionAny barMetrics:UIBarMetricsDefault];
[[UINavigationBar appearance] setShadowImage:[[UIImage alloc] init]];

123.不能把jpg格式的图片,直接改成png,这样模拟机上能看见,真机上看不见

124.设置底部tabBar,只需要在AppDelegate.m中引入写好的tabBarController的h文件,并

self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
KeanTabBarViewController * tabBarController = [[KeanTabBarViewController alloc]init];
self.window.rootViewController = tabBarController;
[self.window makeKeyAndVisible];

125.Thread 1: signal SIGABRT类型的错误,实际上都是具体的某种内部的错误,然后最终传递到上层的thread的,而报此错误的。
而解决了内部的具体的错误,此种thread的signal SIGABR,也就算是解决了。
其实thread 1 breakpoint 1.1不是你的程序出错,而是你人为(应该是不小心设置了)的为某一行程序添加了breakpoint,所以xcode就在那儿停了。

126.如果断点指向内存,那么就是初始化时分配内存时出了问题

127.真机调试:设置 -> 通用 -> 描述文件 -> "你的AppleID" 选择信任

128.launchImage有时候会出现第一次运行显示不正常的情况,一般把App删除重新run一遍就好了。

129.延迟进程

//延迟线程进程3秒(目的为了延长LaunchImage的显示时间)
[NSThread sleepForTimeInterval:3.0];

130.ios 支持多个层次的多线程 编程,层次越高的抽象程度越高,使用起来也越方便,也是苹果最推荐使用的方法。

131.苹果不允许修改launchImage的显示时长,所以要想延长启动页的显示时间,就需要对线程的进程进行适当的阻塞,来达到延长启动页的停留时间,也就是延迟线程进程

132.com.公司名.项目名

133.撤销键盘
//点击return撤销键盘

-(BOOL)textFieldShouldReturn:(UITextField *)textField{
    [self.account resignFirstResponder];
    [self.password resignFirstResponder];
    return YES;
}

//撤销键盘

-(void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event{
    [self.account resignFirstResponder];
    [self.password resignFirstResponder];
}

//其实最简单的还是

[self.view endEdit:YES];

134.同一个controller切换界面时一定要刷新一遍

135.隐藏首页NavigationBar
//隐藏首页NavigationBar
这个问题曾经也困扰过我。现在我给出正解。

-(void)viewWillAppear:(BOOL)animated {
    [super viewWillAppear:animated];
 
    [self.navigationController setNavigationBarHidden:YES animated:animated];
}
 
-(void)viewWillDisappear:(BOOL)animated {
    [super viewWillDisappear:animated];
 
    [self.navigationController setNavigationBarHidden:NO animated:animated];
}

注意,animated设为YES,仍是会有一个瞬间的过渡效果。只有设置为animated才能真正实现。

136.如果任意行数,则设置label.numberOfLines=0;

137.设置根据字符串大小自适应的label,在设置outLayout的时候选择Relation的Greater Than or Equal是大于等于该值的效果

138.

[quizCell.photoButton addTarget:self action:@selector(selectImage) forControlEvents:UIControlEventTouchUpInside];
//在controller类中实现cell中控件功能的方法 ,即在controller中找到cell中Button的tag值,然后单击cell中Button时调用controller中的方法

139.view的自适应和label一样要勾选扩展高度

140.在使用自定义view代理执行控制类中的方法时,在调用view视图显示时,无需初始化生成一个UIVIew,直接头文件引用view的类即可

141.

[segment titleForSegementAtIndex:___];
//获取segment文字内容的方法

142.解决xocde7以后出现的使用scollVIew进行约束时自动下移60个位量的问题:使用storyBord进行约束,右下角右数第二个图标,先删除scrollVIew所有约束后,去掉勾选的constrain to magins,进行四周约束,并且更新约束即可

143.reloadInputViews 这个方法重新载入输入视图,一般就是刷新键盘,定义键盘的时候 用这个方法,可惜的是,view无法像tableView那样reloadData更新视图数据,只有手动更新或手绘了

144.其实吧 程序员需要有自己独立的思考,不该当成任务完成一样对照效果图

145.

imageView.userInteractionEnabled = YES;//可以进行对imageView进行手势响应,是手势响应前的必备的一步

146.view视图或cell视图加载缓慢,需要在viewDidload中先将视图加载出来,而不是点击segment后才进行加载

147.自定义搜索:
一个UIView 上面放uitextfield+uiimageview==自定义search

148.先百度、谷歌、找博客,找cocoachina,找github,stackoverflow,再没有,就去研究苹果的官方文档 第三方的官方文档

149.如果想要将上述数据类型的数据永久保存到NSUserDefaults中去,只需要简单的操作(一个Value 一个Key ),例如,想要保存一个NSString的对象,代码实现为


//将NSString 对象存储到 NSUserDefaults 中
NSString *passWord = @"1234567";
NSUserDefaults *user = [NSUserDefaults standardUserDefaults];
[user setObject:passWord forKey:@"userPassWord"];
将数据取出也很简单,只需要取出key 对应的值就好了,代码如下:
NSUserDefaults *user = [NSUserDefaults standardUserDefaults];
NSString *passWord =   user objectForKey:@"userPassWord"];

150.

control reaches end of non-void function  
//缺少返回值
return self

151.

id birthday = [MyUtil getNoneNillObject:responseObject[@"childBirthDay"]];//过滤一遍,防止对象中出现空值导致崩溃,一个防崩处理,遇到空值返回一个空的字符串@"",而不是让其遭遇null或nil无法执行
[MyUtil saveObject:birthday forKey:@"childBirthDay"];//保存要根据要求,而不是说把整个字典保存起来

152.setTintColor是控制的navigationController上所有按钮控件的颜色

153.代理遇到“existing instance variable '1' for property '2' whith assign attribute must be _unsafe_unretained”问题时
例:id <MDSpreadViewDataSource> _dataSource改为id <MDSpreadViewDataSource>__unsafe_unretained _dataSource; 

154.arc自动内存管理,关掉你需要手动释放

155.

[self.dailyAndDietView.upType setTitle:@"疾病种类" forState:UIControlStateNormal];
//设置点击和非点击button的title时 

156.[self.view endEditing:YES]; 键盘立马关闭

157.datePicker设置格式

datePickerView.datePicker.datePickerMode = UIDatePickerModeDate;//显示类型(只显示年月日)
datePickerView.datePicker.minuteInterval = 30;//分钟间隔
datePickerView.datePicker.minimumDate = [NSDate date];//最小日期

158.
不要这样写:

UIDatePicker *datePicker = [[UIDatePicker alloc] initWithFrame:CGRectMake(0, 0, 300, 200)];

这样写分开写就可以改变大小了:

UIDatePicker *datePicker = [[UIDatePicker alloc] init];
datePicker.frame = CGRectMake(0, 0, 300, 200); 


159.时间范围,从当前时间——后面3天

   //时间范围,从当前时间——后面3天
//    NSData * dateMin = [NSDate date];
self.datePicker.minimumDate = [NSDate date];
NSDate * dateMax = [NSDate dateWithTimeIntervalSinceNow:3*24*60*60];
self.datePicker.maximumDate = dateMax;
//自动滚回当前日期


160.KVO模式
KVO,即:Key-Value Observing,它提供一种机制,当指定的对象的属性被修改后,则对象就会接受到通知。简单的说就是每次指定的被观察的对象的属性被修改后,KVO就会自动通知相应的观察者了。

161.dateFormatter显示格式

[dateFormatter setDateFormat:@"yyyy年MM月dd日 EEEE"];EEEE为星期几,EEE为周几
[dateFormatter setDateFormat:@"yyyy-MM-ddHH:mm:ss"];
[dateFormatter setDateFormat:@"yyyy年MMMMd日"];//MMMM 为xx月,一个d可以省去01日前的0



162.注:Objective-C不支持long double类型。@encode(long double)返回d,与double是一样的。

163.objc_property_t
objc_property_t是表示Objective-C声明的属性的类型,其实际是指向objc_property结构体的指针,其定义如下:
typedef struct objc_property *objc_property_t;

164.使用objc_property_t时报错

#import <objc/message.h>
objective_c动行时库已经有这样的功能。使用这些方法需要加头文件
objc_property_t

165.先保留一个方法
//修改datePicker的系统控件

unsigned int outCount;
int i;
objc_property_t *pProperty = class_copyPropertyList([UIDatePicker class], &outCount);
for (i = outCount -1; i >= 0; i--)
{
    // 循环获取属性的名字   property_getName函数返回一个属性的名称
    NSString *getPropertyName = [NSString stringWithCString:property_getName(pProperty) encoding:NSUTF8StringEncoding];
    NSString *getPropertyNameString = [NSString stringWithCString:property_getAttributes(pProperty) encoding:NSUTF8StringEncoding];
    
    //关闭当日高亮属性
    SEL selector = NSSelectorFromString(@"setHighlightsToday:");
    NSInvocation *invocation = [NSInvocation invocationWithMethodSignature:[UIDatePicker instanceMethodSignatureForSelector:selector]];
    BOOL no = NO;
    [invocation setSelector:selector];
    [invocation setArgument:&no atIndex:2];
    [invocation invokeWithTarget:self.datePicker];
    
    
    if([getPropertyName isEqualToString:@"textColor"])
    {
        [self.datePicker setValue:kColorPink forKey:@"textColor"];
    }
    NSArray * array = [[NSArray alloc] initWithObjects:getPropertyName, nil];
    NSLog(@"%@",array);
    NSLog(@"%@====%@",getPropertyNameString,getPropertyName);
}


166.text对齐格式

[nowPickerShowTimeLabel setTextAlignment:NSTextAlignmentLeft];//左边对齐
//text对齐格式

167.记一个关于datePicker选择日期随滚轮实时变动的方法:

 self.datePicker.datePickerMode = UIDatePickerModeDate;//格式 
//默认显示
NSDateFormatter * dateFormatter = [[NSDateFormatter alloc] init];
[dateFormatter setDateFormat:@"yyyy-MM-dd EEEE"];
NSString * dateString = [dateFormatter stringFromDate:[NSDate date]];
self.dateLabel.text = dateString;

[self.datePicker addTarget:self action:@selector(dateChanged:) forControlEvents:UIControlEventValueChanged];//委托

-(void)dateChanged:(id)sender{//动作类
    UIDatePicker * control = (UIDatePicker *)sender;
    NSDate * _date = control.date;

    NSDateFormatter * dateFormatter = [[NSDateFormatter alloc] init];
   [dateFormatter setDateFormat:@"yyyy-MM-dd EEEE"];
    NSString * dateString = [dateFormatter stringFromDate:_date];
    self.dateLabel.text = dateString;
}

168.通过日期求星期

//通过日期求星期
-(NSString*)fromDateToWeek:(NSString*)selectDate
{
    NSInteger yearInt = [selectDate substringWithRange:NSMakeRange(0, 4)].integerValue;//取第0~4位
    NSInteger monthInt = [selectDate substringWithRange:NSMakeRange(4, 2)].integerValue;//取第4位的后两位
    NSInteger dayInt = [selectDate substringWithRange:NSMakeRange(6, 2)].integerValue;//取第6位的后两位
    int c = 20;//世纪
    long int y = yearInt -1;//年
    long int d = dayInt;
    long int m = monthInt;
    int w =(y+(y/4)+(c/4)-2*c+(26*(m+1)/10)+d-1)%7;
    NSString *weekDay = @"";
    switch (w) {
        case 0:
            weekDay = @"星期日";
            break;
        case 1:
            weekDay = @"星期一";
            break;
        case 2:
            weekDay = @"星期二";
            break;
        case 3:
            weekDay = @"星期三";
            break;
        case 4:
            weekDay = @"星期四";
            break;
        case 5:
            weekDay = @"星期五";
            break;
        case 6:
            weekDay = @"星期六";
            break;
        default:
            break;
    }
    return weekDay;
}


169.获取当前年月日,星期

//获取当前年月日,星期
-(int)getCurrentTimeWith:(State)state
{
    NSDate* date = [NSDate date];
    NSCalendar* calendar = [NSCalendar currentCalendar];
    NSDateComponents* comps = [calendar components:(NSYearCalendarUnit|NSMonthCalendarUnit|NSDayCalendarUnit|NSWeekdayCalendarUnit) fromDate:date];
    switch (state) {
        case year:{
            return [comps year];
        }
            break;
        case month:{
            return [comps month];
            break;
        }
        case day:{
            return [comps day];
            break;
        }
        case week:{
            return [comps weekday]-1>0?[comps weekday]-1:7;
            break;
        }
        default:
            break;
    }
}

h.
#import <UIKit/UIKit.h>
#import "InfoView.h"
typedef enum{
    year=0,
    month,
    day,
    week
}State;

//似乎是个可以获得日历属性的方法
NSCalendar日历


170.关掉webview的垂直滑动性,把.bounce关掉,可以试试
还有重写了-(void)scrollViewDidScroll:(UIScrollView *)scrollView方法在webview的scrollView的scrollView.contentOffset.y发生改变时,再设回0 就不滑了

171.写的是tableViewCell里面嵌套webview的,先在自定义单元格类的_webview的懒加载里(我用懒加载添加webview的)设置一下tag值,_webView.scrollView.tag = 11;
在-(UITableViewCell )tableView:(UITableView )tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
设置cell.webView.scrollView.delegate = self;
重写

-(void)scrollViewDidScroll:(UIScrollView *)scrollView
{
    if (scrollView.tag == 11)
    {
        if (_tableView.contentOffset.y < 634.5)
        {
                
            _tableView.contentOffset = CGPointMake(_tableView.contentOffset.x, _tableView.contentOffset.y + scrollView.contentOffset.y);
            scrollView.contentOffset = CGPointMake(scrollView.contentOffset.x, 0);
        }
        else if (scrollView.contentOffset.y < 0)
        {
            _tableView.contentOffset = CGPointMake(_tableView.contentOffset.x, _tableView.contentOffset.y + scrollView.contentOffset.y);
            scrollView.contentOffset = CGPointMake(scrollView.contentOffset.x, 0);
        }
    }
    
}

就实现了Cell里面嵌套webview,同步滑动基本上除了加载慢一点之外,看不出来最后一行Cell用的是网页

有个问题,当页面全部都是webview,也就是我用来展示webview的自定义Cell占满整个屏幕时,pop回上个界面会崩溃,把pop动画关了就好了,因为时间需要响应

172.画线是一定要在drawRect里面的
在view上划一条直线,用到CGContextSetRGBStrokeColor

CGContextSetRGBStrokeColor(context, 1.0, 1.0, 1.0, 1.0);//画笔颜色设置

173.以后遇到编译的Bug就选择xcode的product的cleran,选择一次之后按住option键,再选择cleran build,基本就可以了

174.记一个机智的方法,可以再安装包的resources里找到软件的所偶icns图标

175.改变字体第几个的方法

//应该是改变字体第几个的方法

NSMutableAttributedString *str = [[NSMutableAttributedString alloc] initWithString:@"点击注册代表您已经同意我们的《用户协议》"];
    NSRange strRange = {14,6};
    [str addAttribute:NSForegroundColorAttributeName value:[UIColor colorInSkinWithKey:@"useColor1"] range:strRange];  //设置颜色
    [str addAttribute:NSUnderlineStyleAttributeName value:[NSNumber numberWithInteger:NSUnderlineStyleSingle] range:strRange];


 [_radioButton setAttributedTitle:str forState:UIControlStateNormal];

176.一进入界面的时候会调用tableview的datasource方法,你看是不是数据还没请求到你就使用这个值了

177.一个低级失误

"list" :   {
        "id" : "11c334bc-0c9e-4c20-9b2e-af5e434d4ca7",
        "childId" : "0535001201500246",
        "childName" : "姜依霖",
        "hospitalId" : "0535001",
        "hospitalName" : "招远市人民医院",
        "questionTitle" : "大便频繁,不拉肚子",
        "questionContent" : "宝宝50天,这两天隔两小时就大便,一次就一小坨,肚子不疼,睡觉放屁就拉。醒着也频繁拉。母乳喂养,大便金黄色,宝宝吃睡都正常。以前是一天一次大便,一次拉很多。",
        "questionType" : "医(疾病防治)",
        "submitDate" : 1438764312000,
        "activeFlag" : false,
        "childAge" : 1,
        "childAgeName" : "1个月",
        "readFlag" : false,
        "sex" : "女",
        "hasPic" : false
      }

//这个list是个数组,数组里面是字典,因为有key啊,有key就是字典,取这里面值的时候直接根据字典的key取值就可以了

178.限制textFeild输入内容

//限制textFeild输入内容
-//创建
1.
phonetext = [[UITextField alloc] initWithFrame:CGRectMake(0, 0, self.bounds.size.width-width, 25)];
...... //设置相关属性

2.关联上selector. 注意: 事件要forControlEvents:UIControlEventEditingChanged
[phonetext addTarget:self action:@selector(changePhoneNumValue) forControlEvents:UIControlEventEditingChanged];//手机号码

3.实现selector
-(void)changePhoneNumValue
{
    int MaxLen = 15;
    NSString* szText = [phonetext text];//把输入的字符给szText
    if ([phonetext length]> MaxLen)//如果超过规定长度
    {
        phonetext.text = [szText substringToIndex:MaxLen];//将规定长度的字符保留,并重新赋给
szText
     }
}


179.如果有个cell把delega指向了self,销毁时,assign的时候 必须=nil,weak的时候不必。
weak的时候自动销毁 但是设置delegate的时候是assign 在销毁的时候 一定要delegate=nil
那就是在self的dealloc 再找回这个cell 再delegate=nil
当这个cell不用的时候 =nil 出现的时候 =self 这样做 没意义 而且所有的delegate若是assign的话 在控制器销毁的时候 都应该=nil 不然的话,可能在某一个时间点。当这个控制器销毁的时候,app会蹦掉,那时候你找都找不到在那蹦的,蹦的原因是什么所以,一定要在控制器消失的时候,把assign的delegate全部都=ni

180.

-(void)dealloc{
    self.delegate = nil;
    [super dealloc];
}

181.比如说在界面间传值的时候,对类的初始化,是在用的时候初始化,在全局用变量初始化时实际上最后的结果和使用时的类不是同一个东西,所以,在用的时候再初始化

182.一般传值过去为空,都是初始化的原因

183.long型转化为日期,long型就是1970年到要转换的日期的秒数

        double theDate = [self.theQuestion[@"submitDate"] doubleValue]/1000;
        NSDate * date = [NSDate dateWithTimeIntervalSince1970:theDate];
        NSDateFormatter * dateFormatter = [[NSDateFormatter alloc] init];
        [dateFormatter setDateFormat:@"yyyy年MM月dd日"];
        NSString * dateString = [dateFormatter stringFromDate:date];
        myQuizCell.dateStirng = dateString;
        
        
        

184.那既然仅仅是“更新展示”出已有的数据源,那么为何经常出现这么一个情况,当进行网络请求时,比如将返回数据存放在数组中,在请求内部这个数组是确保拿到了返回的值,确保是有值的,然后在其他地方调用数组时,如果在请求中没有[self.tableView reloadData] ,那么就会造成数组的值为nil,这个是因为异步的原因还是这句话的原因?
可以确定是异步造成的原因,没有加载到数据就开始进行引用,所以需要在引用前就及时的“刷新”数据源,以免造成下面出现空值

185.网络请求成功和失败的返回形式

NSDictionary * parameters = @{@"from":@"ios", @"secretKey":secretKey, @"username":name, @"childId":childId, @"inputDate":date, @"height":height, @"weight":weight};
[AFNetManager postWithUrl:URL_ADDGROWTHMONITOR parameters:parameters success:^(NSURLSessionDataTask *task, id responseObject) 
{
   DLog(@"R: %@",responseObject);//这里只是指参数和地址请求成功,并不代表执行成功
} failure:^(NSURLSessionDataTask *task, NSError *error) 
{
   DLog(@"E: %@",error);//这里表示url地址请求失败
}];

**186.举个例子,实际上加载的collectionView背景色变成黑色,tableView同理self.view.backgroundColor 和 self.collectionView.backgroundColor 是不一样的。**

187.view的一些方法使用情况

  • viewDidLoad-加载视图

  • viewWillAppear-UIViewController对象的视图即将加入窗口时调用;

  • viewDidApper-UIViewController对象的视图已经加入到窗口时调用;

  • viewWillDisappear-UIViewController对象的视图即将消失、被覆盖或是隐藏时调用;

  • viewDidDisappear-UIViewController对象的视图已经消失、被覆盖或是隐藏时调用;

  • viewVillUnload-当内存过低时,需要释放一些不需要使用的视图时,即将释放时调用;

  • viewDidUnload-当内存过低,释放一些不需要的视图时调用

188.设置自定义视图的位置,不要把位置写死

189.//scrlloView使用outLayout约束布局的方法后,设置view的Frame,要使用这个- (void)viewDidLayoutSubviews方法

-(void)viewDidLayoutSubviews
{
    [super viewDidLayoutSubviews];
    [self questionView];//视图加载要在这里,而不是viewDidLoad
}

-(void)questionView{//我要提问
    if (self.customView) {//如果有了 就只执行一次
        return ;
    }
    NSArray * nib = [[NSBundle mainBundle]loadNibNamed:@"QuizView" owner:self options:nil];
    self.customView = [nib objectAtIndex:0];
    
    //获得屏幕的Frame
    //        CGRect tmpFrame = [[UIScreen mainScreen] bounds];
    
    //设置自定义视图的位置,不要把位置写死
    self.customView.frame = CGRectMake(0, self.tableView.frame.origin.y, 320, self.tableView.frame.size.height);//这里不能写死高度,否则scrollview无法滑动
    
    [self.customView.photoButton addTarget:self action:@selector(selectImage) forControlEvents:UIControlEventTouchUpInside];
}

190.ayoutSubviews是UIView中的属性方法,即只要继承于UIView,就可以使用这个方法,这个方法也很强大,以下是他的触发时机:

1、init初始化不会触发layoutSubviews
2、addSubview会触发layoutSubviews
3、设置view的Frame会触发layoutSubviews,当然前提是frame的值设置前后发生了变化
4、滚动一个UIScrollView会触发layoutSubviews
5、旋转Screen会触发父UIView上的layoutSubviews事件
6、改变一个UIView大小的时候也会触发父UIView上的layoutSubviews事件

在这些触发情况下,我们就可以妙用他,比如说改变数据等等,这是个很不错的方法,而且我们也可以手动调用,即

[self setNeedsLayout];

注意:调用layoutSubviews,也需要调用它的父类方法,即 

[super layoutSubviews]

传说如果不调用的话会出现奇怪的问题。

191.当scrollView下滑时,底边控件显示不完时,去设置一下constraints的bottom的constans的约束距离就可以了

192.controller的类在传值的时候是不可以直接Init初始化的,而是要用标识符找到。初始化就会造成你找不到它里面本来声明的参数

193.//这句也可以实现去除tableView顶部空白,即放弃自动调整布局(tableView的scrollView属性的自动布局)

self.automaticallyAdjustsScrollViewInsets = NO;//去除tableView顶部空白


194.如果遇到判断字符串不执行便跳过等一系列问题,那么很可能是在转换和执行条件不符上面出了问题

195.在有navigation的界面中,约束出现问题就最好Push一个有navigation的界面,scrollView底部没有撑满时不会滑动,viewController切换界面的时候要找准方法调用的地方

196.在有scrollView的情况下,加在视图的调用还是应该写在viewDidLayoutSubviews里面

197.git在pull出现非冲突性错误而无法正常继续时,:wq

198.用手势比用单一按钮好,方法要科学

199.对于像textField这种不同于Button本身具有点击事件的控件来说,拖一个关联响应事件相当于调用一个其中的代理方法,只有像button那种touch down才是点击,by the way,textFiled的editing did end就是结束编辑时调用的方法,button取消计时器闪烁的效果,把button定义为自定义类型而不是系统类型即可

200.不要去试图判断颜色相等,这是不可靠的

201.传值理解的不够透彻,会很恼火

202.小结一下:
1.关于光标自动跳转到下一行这种事,直接呼出下一行的键盘就可以实现了
2.如果说在调用的方法中有调回主界面之类的方法后,那么就不要再在下面先执行跳转回根视图之类的操作,尤其是异步的时候
3.保存在字典里的KEY的名字和参数的KEY要分清楚

203.可以暂时理解为,刷新view

[self setNeedsDisplay];

204.以下是用来btn逐渐显示出来用的

[UIView beginAnimations:nil context:nil];
[UIView setAnimationDuration:0.01];
[UIView setAnimationDelegate:self];
[UIView setAnimationDidStopSelector:@selector(endAnimation)];
//在这里设置透明度为0,就会慢慢变成0
[UIView commitAnimations];

205.如果需要推送消息,则要到苹果官网上制作证书,再到环信后台制作推送证书.

206.传值拿到nil几乎都是初始化的问题,内存地址未保存

207.当xib找不到Identifier的时候,极有可能是因为你的xib里面包含了cell外面的其他控件

208.在autLayout设置的时候,当第一个设置好约束后,其余的以其为标准进行设置

209.在UILable中lineBreakMode中有以下几个功能

1.NSLineBreakByWordWrapping = 0 //以空格为边界,保留单词,根据计算结果重新设置UILabel的尺寸 。

2.NSLineBreakByCharWrapping //保留整个字符3.NSLineBreakByClipping //简单剪裁,到边界为止
4.NSLineBreakByTruncatingHead //前面部分文字以……方式省略,显示尾部文字内容

5.NSLineBreakByTruncatingTail //结尾部分的内容以……方式省略,显示头的文字内容。

6.NSLineBreakByTruncatingMiddle //中间的内容以……方式省略,显示头尾的文字内容。

210.在tableView的cell当中,取决于section决定的数组,用indexPath.section决定,取决于row的数组,用indexPath.row决定

211.git冲突时,需要删除的是同时修改的部分,而同时添加的不需要删除

212.你要使用第三方,就要为这个第三方工具的bug负责,不要说到时候我改不了这个bug,是第三方的原因云云

213.关闭cell的点击

-(nullable NSIndexPath *)tableView:(UiTableView *)tableView willSelectRowAtIndexPath:(NSIndexPath *)indexPath
开关开 return indexpath开关关 return nil

214.上拉刷新时需要的逻辑

if([@"success" isEqualToString:value]){            
           [LCProgressHUD hide];            
           [self.tableView.pullToRefreshView stopAnimating];            
           [self.tableView.infiniteScrollingView stopAnimating];            
          if (self.page == 1) {               
                  self.questionInfo = responseObject[@"rtn"][@"body"][@"list"];                            
     }else{                
                  NSArray * array = responseObject[@"rtn"][@"body"][@"list"];                
                  NSMutableArray * tmpArray = [self.questionInfo mutableCopy];//把之前的保存在可变数组中,可变数组就是长度可以变化就是死的可以添加和删除的               
                  [tmpArray addObjectsFromArray:array];//加载到之前数据的身后                
                  self.questionInfo = [tmpArray copy];//再返回给保存的数组,使tableView的number返回行数发生相应改变            
      }           
                  [self.tableView reloadData];        
}

215.BOOL型变量如果不做特别处理,那么其值为no

216.有些开发者,在判断数组是否为空时,会写成
if (array != nil)
或是: if (array.count != 0)
其实严格来说,这两种写法,都是考虑不足并且不稳定的,并且忽略了一种更常见的情况。
首先来说一下,二者之间的区别。
array == nil
这种情况指的是这个array对象是一个nil对象,而不是一个NSArray类型对象。nil对象是一个可以接收任何消息的对象,它可以赋值给任何一个对象,你对它发消息也没什么问题,尽管你得不到你想要的结果。
array.count == 0
这种情况跟上一种不同的在于,此时的array是一个NSArray类型对象,只不过这个array里面没有元素。但它本身是可以作为NSArray对象来使用的。
而事实上,如果你是处理网络请求的数据,取出的array是nil对象是几乎不可能的(至少我没遇到过),多数情况下会出现的是另一种情况:
取到的array是一个NSNull对象。
NSNull是一个特殊的类,它和nil一样,也代表空值,但二者有区别,NSNull不接收NSArray的那些方法,它只有一个类方法:
+(NSNull *)null;
因此发送NSArray特有的方法或属性访问都会导致程序crash。
我们做空值判断的很大一部分原因就是为了在后台接口数据返回一些异常数据的时候,程序能保证稳定性。
举个例子:某些情况下,后台可能由于各种原因,对某个字段返回了null值,这时我们取到的就是[NSNull null]这样一个对象,再比如说,后台可能对某一个数据取值,但取到了0个,这时返回的是一个空组,我们取到的就是@[],空组。
因此判断数组是否为空,需要对各种情况都进行判断。写法有很多种,比如你可以写成:
if (array != nil && ![array isKindOfClass:[NSNull class]] && array.count != 0)

217.iOS从URL加载图片

+(UIImage *) imageFromURLString: (NSString *) urlstring  {      
// This call is synchronous and blocking      
      return [UIImage imageWithData:[NSData  dataWithContentsOfURL:[NSURL URLWithString:urlstring]]];  
}

218.上传image图片时要转换成nsdata格式,转换成jpeg内存小,而且最好压缩成0.几的

219.设置datePickerView的最小日期就可以限制上滚功能

220.真的没有技术解决不了的问题,只是自己觉得麻烦懒得去弄罢了

221.在给一个之前在循环中赋值的控件重新赋值时,要在循环当中实时保存这个控件(或者说实时取到这个控件),然后再取出这个控件进行重新赋值

222.在使用git的时候,要看分支名称是否是master,不是就用其他的

223.app默认横屏
在 info.plist 里增加一个属性 Initial interface orientation  
值有四个选项分别对应四个方向,选 Landscape 开头的就是横着的

224.clang: error: linker command failed with exit code 1 (use -v to see invocation)

ios开发这个错误一定少不了,现总结如下,一般这三方面的问题,如果不是哪你真可麻烦了
1.引用出错,把*.h弄成了.m,检查一下你的所有引用;
2.再就是你引用第三方的库,你添加文件是系统没有所第三方库的.m文件参入的编译中去,你向项目添加文件得注意了;
3.就是不小心添加的重复的类,向Entity之类,具体你可以看这里http://stackoverflow.com/ques...
顺便说一下http://stackoverflow.com/这个网站是iso开发不可少的一个网站;
4.有些frameworks没有添加进来也会出现上面的问题;

225.关于代缩进
你先按command + [把代码往左缩进到最前面再按command + /注释代码最后按command + ]把代码往右缩进
改为 Tab 缩进(非四个空格),再注释,你们就会发现神奇的对齐了。

226.不要懒不要犹豫不要花时间去做无谓的思考,想到就去做就去写,无论是什么试一试总会知道的,敏捷的思维比什么都重要,比浑浑噩噩的细思缜密要清晰的多。

227.如果是有tableView的界面访问接口,需要储存数据,如NSArray, NSDictionary等,千万不要忘记最重要一步,在接口数据获取成功后加上[self.tableView reloadData];这句话,刷新tableView的数据,否则会造成NSArray或NSDictionary为nil,无法获得返回数据

228.运行之后显示崩溃信息:
Terminating app due to uncaught exception 'NSRangeException', reason: '* -[NSMutableArray objectAtIndex:]: index 2147483647 beyond bounds [0 .. 12]'
数组越界,好好检查代码 

229.关于dateFormatter
1)当你的format格式是
NSDateFormatter* dateFormatter = [[[NSDateFormatter alloc] init] autorelease];
[dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"]; // 这里是用大写的 H
NSString* dateStr = [dateFormatter stringFromDate:date];
你获得就是24小时制的。
2)当你的format格式用的是
[dateFormatter setDateFormat:@"yyyy-MM-dd hh:mm:ss"]; // 这里是用小写的 h
你获得的就是12小事制的。

230.大多时候outLayout约束label的时候不需要约束宽度,改变fram就可以了

231.git插件插件没有显示x的时候可以直接pull和push

232.切图是可以切割使其不变形的

233.windows的字体在xcode里字体除以1.8

234.只要cell里的label重写了,是可以直接在controller里给它赋值的

235.记着,改变lable里个别字符的颜色,最重要的一步是

cell.gold.attributedText = attString;

这是在改变label的text,不是直接作用于string

236.数组的count是数组内元素是从1开始的的总体数量,不是数组从0开始的的下标

237.用%@输出,NSInterger转换成整形变量就可以了

cell.day.text = [NSString stringWithFormat:@"%@",@(self.day+1)];

238.如果cell中有特殊类型cell,要优先做判断,否则可能由于条件判断原因(入indexPath.row数量为有限,判断比较值过大时)显示不出来,因为无法执行到该特殊类型的判断所以被略过

239.大多数意外断点停在[indexPath.row]处时,几乎都是由数组越界造成的,因为数组会将indePath.row的所有满足条件执行一遍,会出现indexPath.row大于数组元素数量的情况,即返回行数大于数组数,多余的cell返回行没有数据可执行,而造成崩溃。例:indexPath.row为12,array的元素为10,此时array[indexPath.row]就会造成崩溃。因为一切要以数据为基准

240.要解决cell的复用问题,说白了,就是把判断了的地方再反判断一次,更改了的地方再反更改一次就可以了,上面更改了,下面就也要对这个更改负责

241.想要切割图片,点击右下角的show slicing

242.在-(void)drawRect:(CGRect)rect方法里赋值的时候,基本上相当于写死了,之后再在其他方法里赋值也不会改变,这相当于一开始就给view绘出了的,所以不会改变,这点需要谨慎注意

243.判断星星数量的方法

NSInteger score = [self.array[indexPath.row][@"SCORE"] integerValue];
 //            CGFloat xoffset = 0.0f;            
for (int i = 0; i < 5; i++) {                
    UIImageView *imgview = (UIImageView *)[cell.contentView viewWithTag:i + 11];                
if (i<score ) {                    
    imgview.hidden = NO;                
} else {                    
    imgview.hidden = YES;                
}//                
    imgview.hidden = NO;            
}

244.果然二级运算和一级运算之间还是要加括号的

245.

NSString * theFirst = [answer_phone substringToIndex:3];//截取下标3之前的字符,从0开始

246.Object或Key只能是对象(id或继承自id的),所以字典是不能直接添加整数的

247.

int i = 1;
[dic addObject:[NSNumber numberWithInt:i] forKey:@"somekey"];//或者[dic addObject:@1 forKey:@"somekey"];//取出时
i = [[dic objectForKey:@"somekey"] intValue];
//可以不转换成字符串 

248.直接输出整数

cell.gold.text = [NSString stringWithFormat:@"%@枚金币", @(goldsNumber)];

249.Decimal Pad实数键盘,包括小数点和数字

250.判断字符串中是否含有某一字符

if([roadTitleLab.text rangeOfString:@"qingjoin"].location !=NSNotFound)
//_roaldSearchText            
{                       
    NSLog(@"yes");
} else { 
    NSLog(@"no");
}

251.如果存在如:不同的segment展现同一种内容,但其显示数据方式存在差异,且这种差异可以判断时,通常在网络请求返回的参数中可以有鉴别这种判断的key值,这时最好在获取网络请求参数的类中以key值做出判断。

例:

else if (self.segmented.selectedSegmentIndex == 0){        
    DetailedOfInteractionViewController * detailed = [MyUtil getViewControllerWithIdentifier:@"detailed" storyboardName:@"Interaction"];        
    detailed.theQuestion = self.questionInfo[indexPath.row];
//        detailed.isMyQuestions = NO;                
//判断childId和账号登录时的childId是否相同,如果相同就表示是自己回答的问题,不相同就不是        
NSString * childId = self.questionInfo[indexPath.row][@"childId"];       
NSString * myChildId = [MyUtil getObjectForKey:DATA_LOGIN_CHILDID];        
if ([childId isEqualToString:myChildId]) {            
    detailed.isMyQuestions = YES;        
}else{            
    detailed.isMyQuestions = NO;        
}

252.reuseIdentifier,实际上可以理解为,只是作为tableView的一个重用标识,作记号用,并不是说一定要找到某一处标识过相同字符的控件来调用不可,只是同类的标识而已

253.重用机制调用的就是dequeueReusableCellWithIdentifier这个方法

254.Talk is cheap. Show me the code.

255.“在多写代码的同时,我们也要注意不要”重复造轮子”,尽量保证每次写的代码都能具有复用性。在代码结构因为业务需求需要变更时,及时重构,在不要留下技术债的同时,我们也要多思考如何设计应用架构,能够保证满足灵活多变的产品需求。
在多次重构和思考的过程中,我们就会慢慢积累出一类问题的“最佳实践”方式,成为自己宝贵的经验。”

256.修改textField的placeholder字体的颜色和大小

textField.placeholder = @"username is in here!";  [textField setValue:[UIColor redColor] forKeyPath:@"_placeholderLabel.textColor"];  
[textField setValue:[UIFont boldSystemFontOfSize:16] forKeyPath:@"_placeholderLabel.font"];

257.用来隐藏navigationBar
self.navigationController.navigationBarHidden = YES;

258.单一的点击操作其实设不设置delegate为self都是一样的

259.tableView的cell里隐藏图片直接设置hidden的bool值就可以了,不用在cell类里重新写方法

260.设置button的selected之后,要把button类型改为custom自定义的

261.质量与速度不可得兼吗,我觉得并不是,冲要条件是时间。事前做好准备,便可兼顾。

262.在有scrollView的前提下,设置屏幕居中,要以scrollView为参照物,而不是view

263.git冲突的时候=====下面是别人的,head到=====这里面是自己的

264.关于静态tableView,所谓的静态就是指不通过代码的方式来创建,主要是通过storyboard可视化配置。

265.在init里初始化,比didLoad里靠谱点

266.去除NavigationBar下面的线

self.navigationController.navigationBar.barStyle = UIBaselineAdjustmentNone;


267.代码规范:else前后都有空格

268.count是数量,自然是从1开始,而row之类的是下标,自然是从0开始的,不要加错了。比如:array.count +2,array里面有3个元素,那么,3+2就是5, 而array.count+2 == indexPath.row的时候,左边表示5,而右边表示5的时候其下标恰恰是4(因为从0开始计算),所以就会造成一个计算上的误差,这点需要注意

269.如果在进行网络请求时tableView界面突然崩掉并且意外断点没有指向任何错误处,很可能是在cell中取值赋值时出了问题,比如讲一个字典直接当成数组的值赋值给某个字符串

270.计算label自适应cell高度的时候,网络请求所得到的值记得要通过数组传递过去计算字符串的高度,不要传成字典,这样计算的是字典的高度

271.tableView的cell的单选效果,几句代码就ok,网上的方法都太垃圾了

-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
     GDFollowUpTableViewCell * cell = [tableView dequeueReusableCellWithIdentifier:@"FollowUp"];                
     cell.selectionStyle = UITableViewCellSelectionStyleNone;//点击时无色        
     cell.message = self.array[indexPath.row][@"CONTENT"];                    
     if (self.chooseFlag == indexPath.row){//判断是否被选中            
         cell.okButton.hidden = NO;        
     } else {            
         cell.okButton.hidden = YES;        
     } 
 }
 -(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{    
     self.chooseFlag = indexPath.row;        
     [self.tableView reloadData];
 } 
 
 
 

272.任何的状态判断都可以用全局状态保存来判断

273.如果网络请求持续出错,而参数和地址又没有问题,可以检查参数名称是否全部为大写,后台参数名全部为大写,大小写未区分会报错

274.有个发现的小技巧,点击outLayout的updataFram可以让imageView自适应图片大小,就不用再调整图片清晰度了

275.

self.tableView.tableFooterView = [[UIView alloc] init];//初始化tableFooterView,达到去掉没有数据的cell的目的

276.Swift 语言带来了众多函数式编程的特性

277.状态是函数的魔鬼,无状态使得函数能更好地测试

278.“有一些人总是追赶着技术,有什么新技术不管三七二十一立马就用,结果被各种坑。又有一些人,总是担心新技术带来的技术风险,不愿意学习。结果现在还有人在用 MRC 手动管理引用计数。而我想说,我们需要保持的是一个拥抱变化的心,以及理性分析的态度。在新技术的面前,不盲从,也不守旧,一切的决策都应该建立在认真分析的基础上,这样才能应对技术的变化。”

279.简单工厂模式深入分析: 
简单工厂模式解决的问题是如何去实例化一个合适的对象。  
简单工厂模式的核心思想就是:有一个专门的类来负责创建实例的过程。  
具体来说,把产品看着是一系列的类的集合,这些类是由某个抽象类或者接口派生出来的一个对象树。而工厂类用来产生一个合适的对象来满足客户的要求。  
如果简单工厂模式所涉及到的具体产品之间没有共同的逻辑,那么我们就可以使用接口来扮演抽象产品的角色;如果具体产品之间有功能的逻辑或,我们就必须把这些共同的东西提取出来,放在一个抽象类中,然后让具体产品继承抽象类。为实现更好复用的目的,共同的东西总是应该抽象出来的

280.简单工厂模式(Simple Factory Pattern)属于类的创新型模式,又叫静态工厂方法模式(Static FactoryMethod Pattern),是通过专门定义一个类来负责创建其他类的实例,被创建的实例通常都具有共同的父类。

281.回调是执行后回调“我”来完成,通知是通知后“我”主动去完成

282.在tableView的didSelecte里传值的时候,不能在cellForRowAtIndexPath里赋值了再拿来用,因为cellForRowAtIndexPath会给每一个都赋值,而didSelecte只是当前选中的cell,会造成内存问题报错

283.如果xcode archive 一直是灰色的,当配置是模拟器的时候, archive就是灰色的。当把配置选择为device才能选 archive。

284.object-c中绝对值是labs()形式的,c中是abs()

285.这个方法可以随着输入实时改变

-(void)textViewDidChange:(UITextView *)textView

286.目前应用开发的核心就是数据处理和展示

287.当重写控件时,控件类型声明的参数名,如:(textField *)textFiled,所打印出的数据为整个控件的全部属性的数据,如fram,内部属性等

288.善用回调

289.其实很多东西并没有别人说的那样复杂,方法多种多样,如果觉得功能简单,那么实现出来的方法就绝对不会难,其实每次自己去想一想功能的执行逻辑和顺序,很多东西就都迎刃而解了

290.在全局当中声明一个cell时,在viewDidLoad里将其属性设置好,不要忘记将自定义的cell注册,然后使用其标识符,在cellForRowAtIndexPath方法中如果只有一行cell,那么直接return这个cell就可以了,不需要再进行任何设置了

291.业务逻辑要熟悉清楚

292."刚刚说到,在类中完全使用 _property 的方式来访问私有成员变量,是不会有内存管理上的问题的。但是使用 self.property 的方式来访问私有变量是不是也是一样不会有内存管理上的问题呢?确实也是,但是有一点需要注意:我们最好不要在 init 和 dealloc 中使用 self.property 的方式来访问成员变量,这一点是写在苹果的官方文档里的,我在以前的文章里也介绍过。(见:《不要在init和dealloc函数中使用accessor》)
所以,如果你用 self.property 来访问私有成员变量。那么你需要注意,在 init 和 dealloc 中不使用这种方式。这其实对程序员来说是一个负担,你需要不停提醒自己有没有犯错。如果你使用完全的 _property 的方式来访问私有成员变量,就不用想这一类问题了。"

293."我之前 Review 过一个同事的 iOS 端代码,那个同事喜欢把 table view 的数据另外封装成一个类,而我觉得这些数据其实就是一个数组,没必要进行这一层封装,最终我们争论了比较久。我的观点是,一切隐藏都是对代码复杂性的增加,除非它带来了好处,例如达到了代码复用,提高了代码的可维护性等,否则,没有好处的封装只会给代码阅读理解带来成本。就我现在的经历中,大部分的 table view 的数据都可以放在一个数组中,没必要把这个数组封装起来,另外提供一套操作这个数组数据的方法。"

294."我之前从来没想到过这两者之间的速度和应用体积会有很大差别。不过一个同行(来自国外著名的社交网络公司)告诉我,他们公司发现二者还是有不小的差距,如果你们的应用需要做一些深度优化,可以考虑一下把 self.property 换成 _property。但我觉得,大部分应用都应该是不需要做这种深度优化的。"

295."是的,如果用 _property 这种写法,就不能使用 KVO 和 KVC 了。但是我得反问一下,在一个类的内部,KVO 自己的私有成员变量算是一个好设计吗?我们讲类要”高内聚,低耦合”,KVO 是为了实现观察者模式,让对象之间相互解耦的。如果把 KVO 用在类的内部,KVO 自己的私有成员,我认为其实这不是一个很好的设计。"

296."在 Swift 中,引入了 Computed Properties 的概念,其实这在 Objective-C 中也有,只是没有专门给它名字。如果一个 property 我们提供了对应的 setter 和 getter,并且没有直接使用其对应的 _property 变量,那么这个 property 就是所谓的 Computed Properties。
是的,在类的内部如果直接使用 _property 形式,也无法使用 Computed Properties 了,但我认为这影响不大。其实 Computed Properties 也就是一层对数据存取的封装,我们另外实现两个函数,分别对应数据的 setter 和 getter 功能,就可以达到同样的效果。"

297."直接用私有变量有个需要特别注意的地方,在 block 里直接写 _property 相当于 self->_property,虽然没写 self,但是暗含了对 self 的retain,容易造成循环引用。要记得用 weakSelf/strongSelf 大法。这一点确实是被很多人忽视的"

298."上面提到的这些问题都是小问题,影响不大。但是代码风格的统一却是大问题。所以不管你们项目中使用的是 self.property 风格还是 _property 风格,问题都不大,但是如果你们同时使用这两种风格,那么就非常不好了。"

299.在tabelViewController中的顶部加一个view

UIView * sengmentView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, self.tableView.frame.size.width, 68)];
self.tableView.tableHeaderView = sengmentView;//将tableView的headerView替换成我们要添加的view


300.改变滑动删除的文字内容

-(nullable NSString *)tableView:(UITableView *)tableView titleForDeleteConfirmationButtonForRowAtIndexPath:(NSIndexPath *)indexPath
 {    
    NSString * string = @"设置";    
    return string;
 }
 
 
 

301.在tableView的不同section之间加上header

-(NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section{ 
   if (section == 0) 
{        
    return @"";   
 } else {        
    return @" ";    
}

302.collectionView cell上下左右边距

return UIEdgeInsetsMake(1, 13, 1, 1);

303.在 Swift 的世界里,一切皆对象

304.编程和科研是很相近的两个职业

305.在重新开发版本时,如果不使用cocospod,那么,在引用之前使用过的第三方类时,只需要将类复制到新的项目的文件夹内即可,不要复制整个文件夹,会造成不必要的麻烦

306.复制和拷贝在mac环境下的效果是不一样的

307.在设置tabBar之后,要在appDelegate里给其制定一个rootViewController

308.//获取当前版本号

//获取当前版本号
    NSDictionary *infoDictionary = [[NSBundle mainBundle] infoDictionary];
    NSString *app_Version = [infoDictionary objectForKey:@"CFBundleShortVersionString"];
    
    

309.当tableView底部出现大量空白又不想要时,可以把tableView的view的背景色设为clean,然后将controllerView的背景色设置一下就可以了

310.关闭tableView滚动,实际上tableView是一个scrollView

self.tableView.scrollEnabled = NO; 

311.顺便说一句,当隐藏tabBar的时候,如果controllerView上有tableView,那么此时你需要用下面这段代码来让tableView顶部不留下空白部分,适配时,scrollView顶部有空缺,也可使用此方法解决,意思是关闭scrollView的自动适配:

self.automaticallyAdjustsScrollViewInsets = NO;

312.关于collectionView使用时需要注意的地方

  • 注意,每一个item之间是存在间距的,所以要预留出间距,否则会超出预设宽度

  • 还有一点,collectionView的默认颜色就说黑色,出现黑色不是黑屏,只要调整一下背景颜色即可

313.如果要使用接口数据赋值,那么直接在网络请求里赋值即可,在外面赋值由于是异步情况会导致无法及时获得

314. 网络解析获取后台的图片

NSString * picture = [NSString stringWithFormat:@"%@%@%@", SERVER_IP,self.array[indexPath.row][@"Picture"],API_KEY];
cell.goodsImage.image = [UIImage imageWithData:[NSData dataWithContentsOfURL:[NSURL URLWithString:picture]]];

315.判断switch是否处于开闭状态

cell.switch.on = YES;
cell.switch.on = NO;


316.跳转返回时有tableView的界面出现下移

//处理方法
-(void)viewWillAppear:(BOOL)animated
{
    self.automaticallyAdjustsScrollViewInsets = NO;
}

317.向后台上传图片转格式

NSData * imageData = UIImageJPEGRepresentation(self.goodsImage.image, 0.3);
//如果是需要转换为base64的格式,还需要加一句
goodsImage = [imageData base64EncodedStringWithOptions:0];


318.一般情况下,用做网络请求的paramaters字典中只存储字符串形式的参数

319.判断字典中元素为空

NSDictionary * dic;

if([dic count] == 0)

{

    //....

}

320.如何查看后台返回的数据储存类型
直接打印出 responseObject的属性查看
例如出现:<__NSCFArray 0x7fcedb4571a0> 说明返回类型为数组
不过一般情况下来说,后台返回的基本都是以数组的形式居多,但也有例外,所以具体情况具体分析,一切以数据为中心
如果只返回了诸如:

Printing description of self->_dic:
{
    BankCardNumber = 6214651002673886;
    BankName = "\U91cd\U5e86\U519c\U6751\U5546\U4e1a\U94f6\U884c.\U6c5f\U6e1dIC\U501f\U8bb0\U5361";
    CreateTime = "/Date(1458116833893)/";
    ID = 14;
    Phone = 13527310193;
    TypeId = 1;
    UserId = 171;
    UserName = "\U54e5\U54e5";
}

这种情况,如果是用字典储存,那么只要去取数组的第0个就可以了,用数组储存就不需要特殊处理

321.判断后台返回的对象是否为空的判断方法

if (responseObject isEqual:[NSNull null])

322.iOS开发gcd问题
并发队列可以保证按照加入队列的顺序取出任务,但是能不能保证这些任务就是按照顺序执行的。比如说任务1先加入队列,任务2后加入队列,有没有可能这两个任务被取出之后任务2先执行呢?
答案是:任务1一定先开始执行 (不一定先结束).

323.进入界面就要调用接口的方法最好写在这里面

-(void)viewWillAppear:(BOOL)animated

324.意外断点打在哪里,几乎就可以断定问题就出现在哪里,只要注意查看断点停留出的地方处理方式,就可以解决问题

325.评分

NSInteger score = [self.replyArray[indexPath.section][@"Value"] integerValue];
    //            CGFloat xoffset = 0.0f;
    for (int i = 0; i < 5; i++) {
        UIImageView *imgview = (UIImageView *)[cell.contentView viewWithTag:i + 11];
        if (i < score ) {
            imgview.image = [UIImage imageNamed:@"xing_okimg"];
        } else {
            imgview.image = [UIImage imageNamed:@"xing_noimg"];
        }//                
//            imgview.image = [UIImage imageNamed:@"xing_okimg"];

326.关于cell自适应label高度出现布局错乱问题
1.检查outLayout是否约束正确,如果该行cell高度不见,请检查底部约束
2.声明一个全局的cell

@interface SSShopEvaluationViewController ()<UITableViewDataSource, UITableViewDelegate, notReplyDelegate>
{
    SSEvaluationTableViewCell * myCell;
    SSAlreadyReplyTableViewCell * alreadyCell;
}
 

记得在viewDidLoad里注册

myCell = [self.tableView dequeueReusableCellWithIdentifier:@"Evaluation"];


327.视图效果应该在视图里写,控制器就让它负责数据

328.同种类型的处理方法写的太多会导致机械化的习惯,思维会变得僵化,整个思路模式容易固化,不要被日常工作的繁琐拖垮了思考的灵性

329.永远不要试图在cell的-(void)drawRect:(CGRect)rect方法中进行状态保存,一旦写入这个方法中就算写死了,再也改变不了。
就比如一个用户交互的开关状态,不要写在这里面,去在controller的cell方法中去判别

330.在做cell自适应label高度时候,一定要固定label的宽度,不需要担心宽度固定小机型会超出等问题,因为在cell中是不会超出的,且左右做了约束已经

331.swift被赋值的对象如果不发生改变或不被修改,那么就将其声明为let常量

332.NSString stringWithFormat 不足多少位时自动补齐0

self.mCurrentTimeLabel.text = [NSString stringWithFormat:@"d:d",minute,seconde];
不足两位时用0补齐
 
 
float f = 12.34;
string = [NSString stringWithFormat:@".2f",f];
NSLog(@"%@", string);
_____12.34
_代表空格   这样只有使用字符串替换的方法用0替代空格


333.swift点击按钮界面跳转

@IBAction func goListButton(sender: UIButton) {
        let myStroyBoard = self.storyboard
        let listView:UIViewController = (myStroyBoard?.instantiateViewControllerWithIdentifier("list"))!
//        self.presentViewController(listView, animated: true, completion: nil)
                //上面这句表示,从下向上跳出一个controller
        self.navigationController?.pushViewController(listView, animated: true)
    }
    
    
    

334.swift UILabel居中

label1.textAlignment=NSTextAlignment.Left  
label2.textAlignment=NSTextAlignment.Center  
label3.textAlignment=NSTextAlignment.Right 


335.swift中tableView的cell点击无色

cell.selectionStyle = UITableViewCellSelectionStyle.None


336.关于swift中let 和 var的用法简单距离

//读取数组中的颜色
var colorArray:[UIColor] = [UIColor .greenColor(), UIColor .blackColor(), UIColor.orangeColor(), UIColor.grayColor(), UIColor.yellowColor(), UIColor.blueColor(), UIColor.brownColor(), UIColor.blackColor(), UIColor.purpleColor(), UIColor.redColor()]
 
let value = Int(arc4random() % 10)
let color = self.colorArray[value]
button.setTitle(self.array[value], forState: UIControlState.Normal)
button.setTitleColor(color, forState: UIControlState.Normal)

337.tableView跟随cell数量展开

self.tableViewHeightConstraint.constant = cellNumber * cellHeight;
即tableView的高度约束等于cell的数量*cell的高度

338.后台图片读取到url但是显示不出来时,就是同步和异步的问题,因为存在网络延迟导致图片无法同步读取,所以要使用异步方法来处理

339.当url地址有问题为nil时的解决方案

解决 代码如下:
 NSString * url = [NSString stringWithFormat:@"网址"]; 
 NSString * newUrl = [url stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding];

340.关闭tableView滑动

self.tableView.scrollEnabled = NO; 

341.obeject-c继承

#import <Foundation/Foundation.h>
#import "Shape.h"
@interface Rectangle : Shape{
    int size;
}

342.label自动换行

//老方法已经过时,被替换成如下方法(行数记得设为0)
[self.applyInfoLabel setLineBreakMode:NSLineBreakByWordWrapping];
 
基本上老的UI方法都会被替换成NS方法,当方法被替换找不到头绪时不妨试试

343.在存在scrollview的情况下,想要实现控件始终跟随屏幕底部的效果,只需要将该控件和scrollview始终处于同级状态下设置约束即可

344.今天在实现判断星星数量的时候遇到一个问题,从而引出接触到一个新的概念,我姑且称之为控件数组。就是在某些时候存在大量同类型控件关联大量输出口需要使用类似collection但又不能使用的时候的一种替换方案。
使用方法:

1.关联一个输出口,在Outlet处选择Outlet Collection,然后填写名称,即声明成功一个该控件类型的数组
2.之后把大量相同的类型控件都关联到该输出口合并,从而组成数组中的元素,使用时按照普通数组的使用方法即可
代码demo:
@property (strong, nonatomic) IBOutletCollection(UIImageView) NSArray *xing;
 
NSInteger score = [self.detailePlan[@"DIFFICULTY"] integerValue];
    for (int i = 0; i < 5; i++) {
        UIImageView * imageView = (UIImageView *)self.xing[i];
        if (i < score) {
            imageView.hidden = NO;
        } else {
            imageView.hidden = YES;
        }
//        imageView.hidden = NO;
    }
    
    

345.通常我们使用viewWithTag如下情形:

如果我们用了一个父View,上面放了多个子view, 每个子view都通过从0开始的Tag值来进行标志,以便于后期在像View上直接使用viewWithTag:tag值来取各个子View

而在用[父view viewWithTag:0]取到的view, 发现不是子view, 而是这个父view, 后来才想起苹果文档上提到过一次,tag值较小的,如0-100为苹果保留使用, 而0就是保留着给自己这个view使用的。

对于其它的view, 如scrollview, 则更上面的0, 1,2 都可能会是保留值。 

346.关于平行对齐时的约束
不需要说要垂直v的约束,只要约束参照物相同的top即可

347.cell的优化写法

可以声明一个数组,直接从controller的接口中保存返回的数据
@property (nonatomic, strong) NSDictionary * plan;
 
然后在cell中集中处理显示(并不是处理数据,只是负责数据显示)
-(void)setPlan:(NSDictionary *)plan
{
    _plan = plan;
    NSInteger type = [plan[@"TYPE"] integerValue];
    NSString * bgImageName = [NSString stringWithFormat:@"health_plan_0%@", @(type)];
    self.bgImageView.image = MyImage(bgImageName);
    self.titleLabel.text = getNoneNilString(plan[@"TITLE"]);
    self.subtitleLabel.text = getNoneNilString(plan[@"SUBTITLE"]);
    self.joinedLabel.text = [NSString stringWithFormat:@"%@人已加入", plan[@"TOTAL"]];
    id status = plan[@"STATUS"];
    if (status && !isEmpty(status) && [status integerValue] == 0) {
        self.statusImageView.hidden = NO;
    }else{
        self.statusImageView.hidden = YES;
    }
}

348.字体加粗
选择font右边的"T"图标,选择加粗bold

349.多个Button适配不同机型间距约束
主要是控制左右的间距问题,为了解决不同机型不同宽度对控件造成的影响

350.如何跳转到一个tabBar上

TabBarViewController * tabBar = [[TabBarViewController alloc] init];
        [self presentViewController:tabBar animated:YES completion:^{
            
        }];
        
        
        

351.tableView的cell为nil时如何处理
多半是之前关联在cell上的空间被删除之后没有删除其对应的关联,去把关联一并删除即可

352.当某个cell在该tableView中只存在一个的时候,不需要使用复用

353.如果出现cell滚动很卡的情况
是因为在加载网络图片或其他东西的时候使用了同步方法,更换为异步

354.Initwithnibname执行顺序先于viewdidload

355.再次重申:NSString是只读的,不可修改。
想修改请用可变字符串NSMutableString

356.清空数组的方法 技巧 
Xcode中,会有两种Array, NSArray以及NSMutableArray

在清空的过程中,千万不要使用 Array == nil; 这样不仅清空了数组,同时也把memory释放了,这个object就不存在了

正确的做法是
利用
removeAllObjects; 这样就可以得到想要的效果了

使用nil将会删除整个数组:

[NSArray removeAllObjects];

---- 最近一直忙于项目,总结就顺手记载了笔记里,

已标记关键词 清除标记
©️2020 CSDN 皮肤主题: 编程工作室 设计师:CSDN官方博客 返回首页