[UI]暑假第三周-天气预报仿写总结
网络请求
咱们分四步走
创建任务–接受响应–接受数据–处理数据
里面有些 NSLog 语句 对初学者不建议删去
可以更好的看出来你的程序哪里出现了错误
以下 demo 都抄自我亲爱的学长学姐们
创建任务
- (void)creatUrl {
//1.创建请求地址
NSString *urlString = [NSString stringWithFormat:@"https://geoapi.qweather.com/v2/city/lookup?location=%@&key=0831d727b42a481681f5d40a96a688ab", self.textField.text];
//处理字符
urlString = [urlString stringByAddingPercentEncodingWithAllowedCharacters:[NSCharacterSet URLQueryAllowedCharacterSet]];
//创建URL
NSURL *url = [NSURL URLWithString:urlString];
NSLog(@"%@", urlString);
//2.创建请求类
NSURLRequest *request = [NSURLRequest requestWithURL:url];
//3.创建会话
//delegateQueue 表示协议方法在哪个线程中执行
NSURLSession *session = [NSURLSession sessionWithConfiguration: [NSURLSessionConfiguration defaultSessionConfiguration] delegate: self delegateQueue: [NSOperationQueue mainQueue]];
//4.根据会话创建任务
NSURLSessionDataTask *dataTask = [session dataTaskWithRequest: request];
//5.启动任务
[dataTask resume];
}
简单的介绍是这样的 层层递进 也挺好记的 分五步
URLStr 构成URL的 str
URL( Uniform Resource Locator) 统一资源定位符
URLRequest 请求
URLSession 会话
URLSessionDataTask 会话任务
接受响应
//接收服务器的响应
-(void)URLSession:(NSURLSession *)session dataTask:(NSURLSessionDataTask *)dataTask didReceiveResponse:(NSURLResponse *)response completionHandler:(void (^)(NSURLSessionResponseDisposition))completionHandler {
NSLog(@"didReceiveResponse");
if(self.data == nil){
self.data = [[NSMutableData alloc] init];
} else {
self.data.length = 0;
}
//允许接收数据
completionHandler(NSURLSessionResponseAllow);
}
就这样 没什么好做更改的
接受数据
//接收到数据,该方法会被调用多次
- (void)URLSession:(NSURLSession *)session dataTask:( NSURLSessionDataTask *)dataTask didReceiveData:( NSData *)data {
NSLog(@"didReceiveData");
[self.data appendData: data];
}
一样的 没什么好做更改的
处理数据
//数据请求完成或者请求出现错误调用的方法
- (void)URLSession:(NSURLSession *)session task:( NSURLSessionTask *)task didCompleteWithError:( NSError *)error {
NSLog(@"didCompleteWithError");
if (error == nil) {
//解析数据
NSDictionary *secondDictionary = [NSJSONSerialization JSONObjectWithData:_data options:kNilOptions error:nil];
NSMutableArray *timeArray = [[NSMutableArray alloc] init];
timeArray = secondDictionary[@"location"];
NSLog(@"%ld", timeArray.count);
for (int i = 0; i < timeArray.count; i++) {
NSMutableString *str = [NSMutableString stringWithFormat:@"%@-%@",timeArray[i][@"name"],timeArray[i][@"id"]];
[self.cityArray addObject: str];
}
for (int i = 0; i < self.cityArray.count; i++) {
NSLog(@"%@", self.cityArray[i]);
}
NSLog(@"-----------over");
} else {
NSLog(@"error = %@", error);
}
[[NSOperationQueue mainQueue] addOperationWithBlock:^{
[self->_tableView reloadData];
}];
}
这一部分是对数据进行解析
下面这一句是解析JSON格式传输过来的数据
NSDictionary *secondDictionary = [NSJSONSerialization JSONObjectWithData:_data
options:kNilOptions
error:nil];
然后下面的语句就没有参考性了
根据你的API确定应该用类型来储存和处理你的数据
加油加油
五种传值
属性传值
协议传值
KVO传值
block传值
这个博客就很不错 按着敲一遍(或者复制下来到你的代码里理解一遍) 就能理解了
这里就不赘述了
https://blog.csdn.net/kochunk1t/article/details/119391962
通知传值
这个看上面那篇有点懵 可能是我个人问题
那就看大家的悟性啦
或者再找一遍博客看一看 比如 这个
巧思反省
小巧思
搜索到的新城市的天气详情页面 和 总的已添加城市天气页面 其实是十分相似
- 单个城市所要展现的内容是一样的
- 搜索到的新城市的天气详情页面需要可以添加城市
- 已经添加过的城市要判重
所以 其实可以写成一个页面
- 单个城市是单页的scroolView 多个城市是多页的scroolView
- 如果只有单个城市 并且单个城市不在已添加的当中 则不设置添加的按钮
- 否则设置添加按钮和事件
大反思
我也遇到了请求次数达到上限 复盘了一下我的代码
- 搜索的时候请求太过频繁了 有更改就搜索一次
- 总的已添加城市天气详情页面每次更改数据时也重新请求了数据
- 城市天气总览也一样
还是要节省一点的
- 搜索输入完全后再进行请求
- 保留已有数据 每次添加新城市时将数据储存 而非重新请求
- 如上