ChenYilong / ChenYilong/iOSInterviewQuestions

iTeaTime(技术清谈)【004期】【代号:林肯】

Open
#118 1 comment 0 reactions 0 assignees View on GitHub
note wiki
Dominant language
Swift
Stars
9.5k
Forks
2.8k
PR merge metrics
No merged PRs in 30d

Description

# [iTeaTime(技术清谈)]( https://github.com/ChenYilong/iOSInterviewQuestions/issues/127)【004期】【代号:林肯】

----------

![](http://ww4.sinaimg.cn/large/006tNc79ly1g4wvr2s23oj31sr0q242m.jpg)

----------

出题:微博@iOS程序犭袁
本期代号:林肯

----------









----------

![](http://getwallpapers.com/wallpaper/full/0/3/2/1518585-abe-lincoln-wallpaper-2560x1440-for-tablet.jpg)

从未被讨论过的问题,不公布答案。顺延到下一期。只要讨论过,答案不正确也会提供答案。下面将讨论过的问题公布答案:

今天会从没有修改马甲(马甲格式为【昵称+地区/公司/职位】)的同学中随机抽取几位幸运儿,送出飞机票若干张。待会儿我出题,回答任意一道即可,别人回答过的,不能再回答,交卷时间为出题日第二天20点。因为是自己出的题,大部分网上没有答案。可以讨论,没点名同学,抢答正确后,请自觉补充同类型问题一道供点名同学回答。题目能够精准筛选非技术同学即可,不需要很难。

----------

1【问题】【编程基础】如何用一行代码,互换两个变量的值,且不产生第三个变量。

【方法一】【啥玩意儿啊-iOS-北京,提供答案】利用Swift元组特性:
可以在定义的同时就取出元祖中的值
// 相当于同时定义了三个变量
let (name, age, score) = (“a”, 30, 99.9)

根据这一特性,我们可以这样互换值:
(a, b) = (b, a)

【方法二】【消摇提供答案】
(a = a ^ b) && (b = a ^ b) && (a = a ^ b) 或者这样 a = a ^ b; b = a ^ b; a = a ^ b;

(a = a + b) && (b = a - b) && (a = a - b)
(a = a x b) && (b = a / b) && (a = a / b)

【方法三】【消摇提供答案】
a = ( a + b ) - b * ( b = a );

----------

2【问题】【iOS】如何给view同时加上圆角和阴影?至少给出两种实现方法,使用到的API越高级越好。
【提示】两种方法,答案提示:UIBezierPath,和iOS11 layer有个新的方法
【答案】iOS11的layer是maskedCorners,CACornerMask。

----------

3【问题】【计算机常识】在开发中,我们在重连等场景中,为避免造成过度的资源消耗,我们常常把重试的时间间隔做递增处理,有时是指数级增长方式,比如第1次与第二次时间间隔为2秒,第二次与第三次时间间隔为4秒,然后是8秒,我们有时也按照1,3,5这样的规律递增。这种编程技巧的名称是什么?

【答案】指数退避算法。

----------

4 【问题】【算法】《易传·系辞上传》:“易有太极,是生两仪,两仪生四象,四象生八卦。”,这句话结合下面的几张图,与计算机数据结构中的哪个概念更为相近,描述该概念,越详细越好。问题如下:
六十四卦所在结构中节点数是多少?
六十四卦中的任意一卦,在上述数据结构体系中对应的概念叫什么?
六十四卦中的任意一卦的高度与深度分别是多少?
“完全” 与 “满” 用哪一个,形容下面的图片更为贴切?

![14153248314177 jpg](https://user-images.githubusercontent.com/2911921/57230297-99b24a00-704a-11e9-84d5-36d94cedee5c.gif)

![v2-30f016d2570d0f3717312be92922fb9c_r](https://user-images.githubusercontent.com/2911921/57230491-0af1fd00-704b-11e9-8448-e53a8ec52f92.jpg)

【答案】总体是二叉树,高度是 0 深度是7,节点数是 2ˆ7-1, 满二叉树。参考下图:

![image](https://user-images.githubusercontent.com/2911921/57230539-2826cb80-704b-11e9-9816-f3a99fd567e0.png)

----------

5【问题】【hybrid-app】js与native交互中,js如何调用native方法,native如何调js方法,借助的中间foundation叫什么。给出核心步骤对应函数,重点给出前端和native需要约定联调的部分。【难度🌟🌟🌟】【出题人 微博@iOS程序犭袁】
【提示】推荐 [《一本走心的 JS-Native 交互电子书》](https://github.com/lefex/DSA/issues/16) 。
【答案】【群成员闪舞提供】
native 能直接调用 js
[webView stringByEvaluatingJavaScriptFromString:javascriptCommand];

js 不能直接调用 native 的方法,但是可以间接的通过一些方法来实现。可以利用 UIWebView 的 webView: shouldStartLoadWithRequest: navigationType: 代理方法来做。 WKWebView 中可以通过 webView: decidePolicyForNavigationAction: decisionHandler:

要想触发native 的 webView: shouldStartLoadWithRequest: navigationType方法,可以通过下面两种形式:
1.创建 iframe 标签
2.设置 window 的 location

核心步骤:
1. native 加载 html,其中的 script 标签里(也就是 js 代码), js 创建 iframe 标签,并设置它的 src 属性为 wvjbscheme://__BRIDGE_LOADED__,并且把回掉放到一个数组里
2.在 webView: shouldStartLoadWithRequest: navigationType 方法中拦截 wvjbscheme://__BRIDGE_LOADED__,并加载本地(桥中)的 js
3.本地(桥) js 创建隐藏的 iframe 标签并且修改 src 为 wvjbscheme://__WVJB_QUEUE_MESSAGE__,这样就又能在 webView: shouldStartLoadWithRequest: navigationType 拦截了。

----------

6【问题】【iOS】猜想dequeueReusableCellWithIdentifier的实现是怎样的,给出示例代码。注意边界条件:相邻cell的identifier相等时。你的实现中该函数的时间复杂度是多少。为什么?【难度🌟🌟🌟🌟】【出题人 微博@iOS程序犭袁】
cell复用机制的实现猜想,见 [GitHub-Chameleon](https://github.com/BigZaphod/Chameleon/blob/84605ede274bd82b330d72dd6ac41e64eb925fd7/UIKit/Classes/UITableView.m#L718) :

```Objective-C
- (UITableViewCell *)dequeueReusableCellWithIdentifier:(NSString *)identifier
{
for (UITableViewCell *cell in _reusableCells) {
if ([cell.reuseIdentifier isEqualToString:identifier]) {
UITableViewCell *strongCell = cell;

// the above strongCell reference seems totally unnecessary, but without it ARC apparently
// ends up releasing the cell when it's removed on this line even though we're referencing it
// later in this method by way of the cell variable. I do not like this.
[_reusableCells removeObject:cell];

[strongCell prepareForReuse];
return strongCell;
}
}

return nil;
}
```

时间复杂度为: O(n)

注意:

`NSArray` / `NSMutableArray`

`containsObject:`,`containsObject:`,`indexOfObject*`,`removeObject:` 会遍历里面元素查看是否与之匹对,所以复杂度等于或大于 O(n)。

这里 `_reusableCells` 使用的是`NSMutableSet`,而
`NSSet` / `NSMutableSet` / `NSCountedSet`

这些集合类型是无序没有重复元素。这样就可以通过 hash table 进行快速的操作。比如 addObject:, removeObject:, containsObject: 都是按照 O(1) 来的。需要注意的是将数组转成 Set 时会将重复元素合成一个,同时失去排序。

加之 for 循环,可以得到复杂度计算结果。

参考:[《深入剖析 iOS 性能优化》](https://ming1016.github.io/2017/06/20/deeply-ios-performance-optimization/)

----------

7【问题】如图:用autolayout做下横竖屏适配:【难度🌟🌟🌟】【出题人 微博@iOS程序犭袁】

里面:蓝色是父视图,子视图是Label和图片,图片可拉伸。Label和图片总是相对居中显示。
对图片顶端,label底端,拉伸,水平总是居中。

Screenshot 2019-04-26 at 8 56 03 PM

【答案】把两个子视图,包一层View,不一定是StackVIew,也可以是普通View,内部搞好约束,top、left、bottom、right。再对中间层view做水平、垂直居中操作即可。

类似前端方案:【十代-小公司-泉州iOS提供】
使用 [**FlexLib**]( https://github.com/zhenglibao/FlexLib ) 框架:

![Pasted Graphic 1](https://user-images.githubusercontent.com/2911921/57230611-50aec580-704b-11e9-86cc-69252098c22d.png)
![Pasted Graphic 2](https://user-images.githubusercontent.com/2911921/57230617-55737980-704b-11e9-8186-d3d0a022b8b6.png)

----------

Posted by [微博@iOS程序犭袁](http://weibo.com/luohanchenyilong/)
原创文章,版权声明:自由转载-非商用-非衍生-保持署名 | [Creative Commons BY-NC-ND 3.0](http://creativecommons.org/licenses/by-nc-nd/3.0/deed.zh)

----------


One more thing...



【非礼勿视】以下为彩蛋部分,建议28岁以上男性观看

----------

![image](https://user-images.githubusercontent.com/2911921/57292671-e6eaf600-70f4-11e9-91d1-4602d9bec00b.png)

Contributor guide

No contributing guide indexed for this repository

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.