20
回答
记一次面试过程
终于搞明白,存储TCO原来是这样算的>>>   

6年PHP,最近打算跳槽,面试了一家公司,大公司。

我的情况,技术一般般吧,理论知识比较欠缺,比较标准的码农;目前带小团队,做的项目最高到 5万QPS的量。

这次被打击到了,简单说下其中一些问题吧。

1. MySQL 事务隔离等级有几个,都是什么?  (看过,但一个都没记住...)

2. 说说设计模式 (我就记得 工厂,单例)

3. redis/memcache 的区别 (我对memcache真的是一点都不了解... 泪崩)

4. cooike和session的区别(cookie长度限制,后来百度知道大概4K)

5. InnoDB和MyISAM的区别 (只记住了事务,行锁,行数统计)

6. Redis持久化方式对比 (当初随便看了一下,只记得两种... 因为都有运维处理,不需要我关系呀~~)

7. redis 的有序集合是怎么实现排序的(并没了解过)

8. 缓存雪崩 (我对概念本来就比较模糊,大概的意思我是知道的,就是表述没说好,这是最后一个问题,我已经看出来面试官不耐烦了--!,然后就出门了~)

 

我不是说面试官有不对哈。确实是自己记性太差。回来赶紧恶补一下各方面知识,以备后面使用。

另外,我觉得我的主要能力,

1. 编码(毕竟码农)

2. 业务能力(经常和产品等扯需求)

3. 分析问题,解决问题的能力(带小团队,遇到一些问题还是我来处理)

4. 应对高并发的能力(5万QPS 也不算低吧,我们系统设计的是极限是10W,当然没到过~)

说实话,情绪有点低落,面试过程有点憋屈。当然,也是给我提醒下,面试需要多准备点!

<无标签>
举报
老陌
发帖于4个月前 20回/2K+阅
共有20个评论 最后回答: 3个月前

1.MySQL事务隔离级别
READ-UNCOMMITTED(读未提交):其他事务可以看到当前事务中没有提交的修改,会导致脏读:一个事务读到另外一个事务还没有提交的数据.
READ-COMMITTED(读提交):大多数数据库默认的隔离级别,避免了脏读,但会导致不可重复读:两次执行同样的查询,可能得到不一样的结果.
REPEATABLE-READ(可重复读,InnoDB默认):实现可重复读,保证同一事务多次读取同样的记录的结果是一致的.但仍避免不了幻读,不过InnoDB用多版本并发控制MVCC解决了幻读的问题.
SERIALIZABLE(串行化):串行化在事务开启时上读锁,在事务提交或回滚时释放锁.通过强制事务串行化,避免出现幻读.
简单说就是在读取的每一行数据上都加锁,所以可能会导致大量的超时和锁争用的问题,实际需要并发的场景很少使用.

 

3.Redis/Memcached区别
Memcached的value类型就只有字符串(string).
Redis的value类型除了字符串(string),还支持列表(list),集合(set),有序集合(sorted set),哈希(hash)等.
Redis支持的订阅发布(sub/pub)的消息通知功能,Memcached也是没有的.
Memcached默认使用LRU清理内存,可能会导致某些数据被删除,所以Memcached不能用过写缓存.
Redis默认设置是noeviction(不回收),内存不够直接报错,可以用来做写缓存.
Redis支持的RDB和AOF两种数据磁盘持久化,Memcached也是不支持的.

 

4.Cooike和Session的区别
Cookie分布在客户端,Session集中在服务器.
Cookie大小有限制(4KB,包括名称+内容+过期时间等),同一域名数量也有限制.
Session的ID存储到客户端时一般使用Cookie.
Cookie由浏览器根据过期时间清理.
Session由服务器清理.

 

5.InnoDB和MyISAM的区别
InnoDB支持事务,行锁,外键,这些MyISAM都不支持.
InnoDB并发写性能比MyISAM高.
InnoDB是根据主键聚集索引组织数据,MyISAM不是.
MyISAM并发写时有表损坏的风险.
关闭MySQL服务后,MyISAM支持直接拷贝索引和数据文件实现表的备份,InnoDB一般不能这样干.
相同的数据量,InnoDB占据的磁盘空间要比MyISAM多.
没什么特殊原因,选择InnoDB不会错.

 

6.Redis持久化方式对比
Redis提供了RDB和AOF两种持久化.
我的理解是RDB是全量备份,AOF则类似MySQL的binlog,遇到写操作则追加到aof文件.
RDB全量备份消耗的时间长,如果你要尽量避免数据丢失,应该用AOF.
AOF的配置 appendfsync always 表示每当Redis执行写命令,就立即把数据写入aof文件,最安全,但速度最慢.
appendfsync everysec 则表示每秒钟写一次,也就是有丢失前1秒数据的风险,但性能要比实时写入好得多.
Redis的appendfsync对比到MySQL就是innodb_flush_log_at_trx_commit和sync_binlog.

 

7.Redis的有序集合是怎么实现排序的
Redis的有序集合(sorted set)的有个权重score,Redis会根据你插入的内容的权重作为排序依据进行写入.

 

8.缓存雪崩
缓存雪崩应该是指Redis缓存过期或不存在时,瞬间的高并发请求会穿透Redis查询MySQL导致数据库负载急剧变大.
我的想法就是,缓存过期或不存在,更新Redis缓存时,加一个锁,让获得锁的那个请求去查询MySQL生成缓存.

<?php
// 参考 http://huoding.com/2015/09/14/463
$key = 'cache_create_lock'; //锁的名称
$value = sha1(uniqid(getmypid().'_'.mt_rand().'_', true)); //唯一值
$ttl = 10; //ttl表示超时时间time to live,单位是秒.
//加锁: nx表示not exists. ex表示expire.
if ($redis->set($key, $value, array('nx', 'ex' => $ttl))) {
    $cache->create(); //加锁后执行业务逻辑,这里是生成缓存
    //加入唯一值判断是为了避免删除到其他操作的锁
    if ($redis->get($key) === $value) {
        $redis->del($key);
    }
} else {
    //缓存失效,又拿不到锁生成缓存,怎么办?直接返回请求失败?
    //缓存失效和命名是计算机科学两大难题.
}

 

--- 共有 5 条评论 ---
eechen回复 @老陌 : 你说的过期和重启不就是我说的"Redis缓存过期或不存在时"这个条件么?不优化,结果都是穿透Redis直查MySQL,没什么不同. 4个月前 回复
JPer雪崩不是这个概念,你搞错了 4个月前 回复
老陌雪崩一般是 同一时间缓存大面积过期或缓存服务器重启,出现大量DB读写。 你说的这个是缓存穿透,两个概念 4个月前 回复
eechen回复 @lymos : 鸟哥和峰哥那种才是PHP大神,我只不过是只小小鸟. 4个月前 回复
lymos php界大神 4个月前 回复

这些问题没一个鸟用, 都不知道都不影响工作,这不过是面试的一个敲门砖,比如说设计模式,我管他妈什么模式,管我鸟事,楼主大可不必丧气,你下面也说了你的主要能力,我看很好

--- 共有 3 条评论 ---
hitank1 回复 @老陌 : 设计模式很好用呀,我读了设计模式的书之后有种豁然开朗的感觉,设计模式可以起到规范或者引导的作用,写代码的时候自觉想到要遵循6大设计原则,避免给别人或者给自己挖坑。自从用了设计模式之后,腰也不酸了,腿也不痛了 4个月前 回复
SingZhang老哥,顶你,有理 4个月前 回复
老陌确实是感觉用处不大,平时都是了解一点,真需要了才查资料。就是打算跳槽的话,就需要回顾一下 4个月前 回复

没事,工作久了出来面试开始总会不太适应,多面面就好。可以先选几个备胎练练手。

--- 共有 1 条评论 ---
老陌这个办法不错 4个月前 回复

工作中基本用不到, 但是想用到我也不知道去哪里了解, 因为我根本不知道有这些东西.

这个行业好难...

顶部