【秋招】字节商业化技术面经 已意向
一面
- 项目
- react15 16 差异 生命周期的变化以及为什么会变?react fiber
- 微前端
- css样式隔离怎么做(css in js、 bem 、shadow dom)
- position定位
- 跨域解决方案、同源策略
- 正向代理、反向代理
- 实现一个防抖函数 function debounce() {},资源竞态的情况怎么处理?
- 节流
-
console.log(1) setTimeout(() => { console.log(2) }, 0) async function echo() { console.log(5) await Promise.resolve() console.log(6) } echo() requestAnimationFrame(() => { console.log(8) }) new Promise((resolve) => { console.log(3) resolve() }).then(() => { console.log(4) }) console.log(7) 1 5 3 7 6 4 8 2
- 二面
- 实验室是什么
- 如何学习前端
- 学习前端看了哪些书
- 实习做了什么事情
- 简单讲讲对 hooks 的理解
- Hooks 如何模拟类组件生命周期
- 实现 useMemo
- 实现 useScroll
- css 权重如何计算
- dom事件流
- addEventLisenter的第三个参数
- Ts 泛型
-
function geykey<T>(o:T,key: keyof T){ return o[key] }
- 阿里实习项目
-
var obj = { foo() { console.log(this) }, bar: () => { console.log(this) }, [window]: window } console.log(Object.keys(obj)) obj.foo() obj.bar.call(navigator)
三面
- 自我介绍
- 介绍一个自己觉得能体现自己的技术的项目
- js对象数组去重
// 判断对象是否相等 const ans = []; const map = new Map(); arr.forEach((item) => { const key = JSON.stringify(item); if (!map.has(key)) { ans.push(item); map.set(key, 1); } }); return ans; // 引入判断两个对象是否相等 // 判断对象是否相等 const objIsEq = (obj1, obj2) => { if(Object.keys(obj1).length!== Object.keys(obj2).length) return false; if (obj1 instanceof Object && obj2 instanceof Object) { const keys = Object.keys(obj1); // 递归判断 return keys.every((key) => objIsEq(obj1[key], obj2[key])); } if (obj1 === obj2) { return true; } return false; }; /* * @param x {Object} 对象1 * @param y {Object} 对象2 * @return {Boolean} true 为相等,false 为不等 */ var deepEqual = function (x, y) { // 指向同一内存时 if (x === y) { return true; } else if ((typeof x == "object" && x != null) && (typeof y == "object" && y != null)) { if (Object.keys(x).length != Object.keys(y).length) return false; for (var prop in x) { if (y.hasOwnProperty(prop)) { if (! deepEqual(x[prop], y[prop])) return false; } else return false; } return true; } else return false; }
// 看代码说结果
setTimeout(function() {
console.log('setTimeout1');
new Promise(function(resolve) {
console.log('promise0');
resolve()
}).then(function() {
console.log('settimeout promise resolveed');
})
});
setTimeout(function() {
console.log('setTimeout2');
});
const P = new Promise(function(resolve) {
console.log('promise');
for (var i = 0; i < 10000; i++) {
if(i === 10) {
console.log('for');
}
if (i === 9999) {
resolve('resolve');
}
}
}).then(function(val) {
console.log('resolve1');
}).then(function(val) {
console.log('resolve2');
});
new Promise(function(resolve) {
console.log('promise2');
resolve('resolve');
}).then(function(val) {
console.log('resolve3');
})
console.log('console');
- React 异步组件
- react 生命周期 源码相关
- 实现react render函数
function render( vnode, container ) { // 当vnode为字符串时,渲染结果是一段文本 if ( typeof vnode === 'string' ) { const textNode = document.createTextNode( vnode ); return container.appendChild( textNode ); } const dom = document.createElement( vnode.tag ); if ( vnode.attrs ) { Object.keys( vnode.attrs ).forEach( key => { if ( key === 'className' ) key = 'class'; // 当属性名为className时,改回class dom.setAttribute( key, vnode.attrs[ key ] ) } ); } vnode.children.forEach( child => render( child, dom ) ); // 递归渲染子节点 return container.appendChild( dom ); // 将渲染结果挂载到真正的DOM上 }
- AST了解吗?
- webpack
- Style-loader 实现
- loader plugin 区别、实现原理
- webpack常见配置
- 平常看哪些书
#2022校招##面经##字节跳动##前端工程师#