ARTICLE DETAIL

资讯详情

深耕网站视觉设计与运营推广的一线实战洞察。

TME2024校招前端笔试(I)考点解析与备考策略

TME2024校招前端笔试(I)考点解析与备考策略 写在前面这篇不是说“TME笔试答案”的因为我也拿不到官方题库。但前端校招笔试这东西出题思路和考察范围其实有很强的规律性尤其是TME这类体量的公司笔试I通常意味着第一场后续还会有IIIII第一场的题型和难度往往是给整个招聘季定调的。我结合自己这几年的面试经验、带过的应届生反馈以及网上能搜到的各家大厂前端笔试真题把TME2024校招前端笔试I最可能考的、也最值得提前准备的点完整拆一遍。如果你正在准备投递TME或者其他大厂的前端岗这篇内容就是给你划重点用的。核心会覆盖笔试的整体考察范围、JavaScript语言基础与手写代码题、Vue/React框架与工程化题目、算法与编程题、以及最后的时间分配和应试策略。每个部分我都会给出可落地的复习思路不是泛泛而谈。1. 笔试考察范围全景拆解TME前端岗到底在筛什么人先搞清楚一个底层逻辑笔试不是用来招“最会写代码的人”的而是用来快速筛掉不合适的人的。TME的校招笔试I一般时长90到120分钟题型通常是“选择题 简答题 编程题”的组合。题量不算大但覆盖面很广目的就是在有限时间内考察你的知识广度和深度。1.1 从岗位JD反推考点优先级我让不少准备投TME的同学把招聘官网的JD截图发我看过前端开发岗的高频要求基本是这几条扎实的HTML/CSS/JavaScript基础理解浏览器渲染原理熟悉至少一种主流前端框架Vue或React有项目实战经验了解前端工程化、构建工具、性能优化具备一定的数据结构和算法基础加分项有音乐类产品开发经验、熟悉Web Audio API、了解Canvas/SVG笔试的出题就是围绕这几点展开的。JavaScript基础是绝对的重头戏大概占30%到40%的分值框架和工程化占25%到30%算法编程题占20%到30%HTML/CSS和网络基础占剩下的10%到15%。这个比例是我根据近几年TME和其他大厂前端笔试题型的平均分布估算的不是官方数据但大方向不会错。1.2 “I”背后的信息量笔试标题里的“I”值得琢磨一下。这说明至少有两场笔试第一场通常面向某一批学校或某一时间段内投递简历的同学。根据往年经验第一场笔试的难度往往相对友好一些因为后续还有第二场、第三场面试官需要通过多场笔试的对比来校准评价标准。但“友好”不等于“简单”基础题依然会考得很细。比如有次我帮一个学弟复盘某大厂前端笔试选择题里考了[1, 2, 3].map(parseInt)的输出结果。这题看着简单但错误率极高因为它考的是parseInt接收两个参数、map传给回调函数的三个参数这两个函数之间的参数错位。这种题就是典型的“知识点你都学过但组合起来就懵”的考法TME这类公司特别喜欢出。1.3 笔试考察的能力模型我把前端笔试的考察点归纳成一个能力模型供你对照自测能力维度考察形式典型题目分值占比语言基础选择题、简答题原型链、闭包、事件循环35%框架与工程化选择题、简答题Vue响应式原理、webpack配置25%算法与数据结构编程题数组去重、大数相加、递归转迭代25%网络与浏览器选择题HTTP缓存、跨域、渲染流程10%HTML/CSS选择题盒模型、Flex布局5%看完这张表你就该明白前端笔试不是一个“刷题就能过”的考试它考的是你对前端知识体系的理解深度。背答案没用你得真正理解底层原理。2. JavaScript与手写代码题基本功的试金石不管哪家大厂JavaScript基础都是前端笔试的重头戏。TME的笔试选择题里JS相关题目的特点是看起来不难但每个选项都有陷阱。如果不理解底层原理很容易凭印象选错。2.1 高频考点原型链、闭包、this指向这三个概念是JS基础题的“三座大山”TME笔试基本必考。原型链的考法通常是给出一个对象继承关系让你判断属性访问的结果或者问instanceof的判定过程。我建议复习时不要死记结论而是画一遍原型链的指向关系图Function.prototype是一个函数对象Object.prototype是原型链的终点func.__proto__ Function.prototypeFunction.prototype.__proto__ Object.prototype笔试常考的一种变体是Function instanceof Object和Object instanceof Function都返回什么答案是true和true因为Function和Object都是函数它们的__proto__都指向Function.prototype而Function.prototype的__proto__指向Object.prototype。搞懂指向关系这类题就迎刃而解。闭包的考法集中在两个场景一个是循环中var和let的区别另一个是闭包导致的变量共享问题。最经典的例子for (var i 0; i 5; i) { setTimeout(function() { console.log(i) }, 1000) } // 输出 5 5 5 5 5如果把var改成let输出就变成0 1 2 3 4。原因很简单let有块级作用域每次循环都创建了一个新的变量绑定而var是函数作用域所有setTimeout回调共享同一个i循环结束后i已经是5。这个题考了作用域、闭包、事件循环三个知识点性价比非常高。this指向的考题常见于以下四种调用方式的判断function foo() { console.log(this) } foo() // window非严格模式/ undefined严格模式 const obj { foo } obj.foo() // obj const bar obj.foo bar() // window / undefined foo.call({a: 1}) // {a: 1}TME笔试里有一类题特别喜欢考箭头函数和普通函数的this区别。记住一句话箭头函数没有自己的this它的this是定义时所在作用域的this。所以obj.foo()如果foo是箭头函数打印的依然是最外层作用域的this而不是obj。2.2 手写题专项深拷贝、防抖节流、Promise笔试题里的手写代码题一般出现在简答题或编程题的第一小问分值不高但很能拉开差距。根据近年的题目风格以下三个手写题几乎属于必考范围。深拷贝是一个经典的不能再经典的题。笔试时如果你只写JSON.parse(JSON.stringify(obj))大概率只能拿一半分因为面试官期待的是能处理循环引用和特殊类型的实现。我推荐的写法是function deepClone(target, map new WeakMap()) { if (target null || typeof target ! object) { return target } if (target instanceof Date) return new Date(target) if (target instanceof RegExp) return new RegExp(target) if (map.get(target)) return map.get(target) const cloneTarget new target.constructor() map.set(target, cloneTarget) for (let key in target) { if (target.hasOwnProperty(key)) { cloneTarget[key] deepClone(target[key], map) } } return cloneTarget }用WeakMap解决循环引用用new target.constructor()保留数组和对象的类型用instanceof处理Date和RegExp。这套写法面试官一看就知道你是真写过深拷贝不是背的“标准答案”。防抖节流也是高频手写题。防抖debounce的含义是多次触发事件后只在最后一次触发的延迟时间结束时执行一次。节流throttle的含义是在固定时间间隔内只执行一次。我习惯用“电梯关门”和“技能冷却”来记忆这两个概念——防抖像电梯人不断进出就不断重新计时节流像游戏技能放完必须等CD。// 防抖 function debounce(fn, delay) { let timer null return function(...args) { if (timer) clearTimeout(timer) timer setTimeout(() { fn.apply(this, args) }, delay) } } // 节流 function throttle(fn, interval) { let last 0 return function(...args) { const now Date.now() if (now - last interval) { last now fn.apply(this, args) } } }Promise相关手写题在TME笔试里出现的频率也很高常见的是Promise.all和简易版Promise。Promise.all的实现需要你理解接收一个可迭代对象返回一个Promise全部成功才成功一个失败就失败。Promise.myAll function(promises) { return new Promise((resolve, reject) { const results [] let count 0 if (promises.length 0) { resolve(results) return } promises.forEach((p, index) { Promise.resolve(p).then(res { results[index] res count if (count promises.length) { resolve(results) } }).catch(reject) }) }) }2.3 事件循环与异步顺序题翻车重灾区TME笔试的JS选择题里事件循环相关题目是错误率最高的题型之一。这类题综合考察宏任务、微任务、异步回调的执行顺序。经典真题长这样console.log(script start) setTimeout(function() { console.log(timeout 1) }, 0) Promise.resolve().then(function() { console.log(promise 1) }).then(function() { console.log(promise 2) }) console.log(script end)正确答案是script start、script end、promise 1、promise 2、timeout 1。口诀是同步先执行微任务先于宏任务宏任务按注册顺序执行。很多人栽在promise 2和timeout 1的顺序上因为不清楚单次宏任务执行完后要把当前微任务队列全部清空才会执行下一个宏任务。更变态的考法是在微任务里继续注册微任务比如Promise.resolve().then(() { console.log(micro 1) Promise.resolve().then(() console.log(micro 2)) }) setTimeout(() console.log(macro 1), 0) // 输出顺序micro 1micro 2macro 1只要记住“微任务队列是连续清空的”这类题就不会错。3. Vue与React框架题实战能力的第一道门槛TME的前端技术栈以Vue为主部分团队用React。笔试的框架题不会考“你用了某个API没有”而是考你对框架底层机制的理解。这就意味着如果你简历里写了熟悉Vue那Vue的响应式原理、生命周期、组件通信这三个点你必须能讲清楚。3.1 Vue响应式原理从Vue2到Vue3的进化Vue相关笔试题目中出现频率最高的就是响应式原理。Vue2用Object.definePropertyVue3用Proxy两者对比是经典考题。Vue2的响应式实现思路递归遍历data对象的每个属性用Object.defineProperty拦截get和set在get中收集依赖Watcher在set中通知依赖更新对于数组重写push、pop、shift、unshift、splice、sort、reverse七个方法Vue3的响应式实现思路用Proxy代理整个对象拦截get、set、has、deleteProperty等操作依赖收集用WeakMapMapSet的数据结构惰性响应式访问到某个属性时才进行依赖收集笔试简答题如果问“Vue2和Vue3响应式的区别”你要答出三个关键点一个是API层面的差别Object.definePropertyvsProxy一个是性能层面的差别Vue3可以代理整个对象不需要递归遍历访问时按需代理还有一个是能力层面的差别Vue3可以直接监听属性新增和删除Vue2需要用Vue.set或者this.$set。能把这个逻辑捋清楚基本就能拿满分。3.2 组件通信与生命周期小题大考的典型组件通信的考题形式通常是选择题给你几个父子组件传参的场景让你选出正确的写法。复习时掌握这张表就够通信类型Vue实现方式React实现方式父传子propsprops子传父$emit触发自定义事件回调函数兄弟通信EventBus / provide-inject状态提升 / Context跨层级Vuex / PiniaRedux / Zustand生命周期方面Vue笔试常考的是“在哪个钩子里发起请求”。标准答案是created或mounted但TME这类公司会更进一步追问“两者有什么区别”。其实核心区别在于created时DOM还未挂载mounted时已挂载如果请求结果需要操作DOM放mounted更保险如果请求结果不依赖DOM放created可以先发请求节省时间。React那边对应的就是componentDidMount和useEffect。3.3 工程化与构建工具笔试里的“隐形考点”前端工程化很少单独出大题但选择题里一定会带几道。最常考的是webpack的核心概念和构建优化。webpack的核心概念包括entry入口、output出口、loader转换器、plugin插件、mode模式。笔试喜欢考的是loader和plugin的区别。理解方式很粗暴loader是处理文件转换的比如把ES6转成ES5、把Sass转成CSSplugin是做loader做不了的事的比如打包前清理目录、压缩代码、注入环境变量。构建优化相关的考题可能会问code splitting代码分割的原理是什么tree shaking摇树优化依赖什么特性才能生效前者答“把代码拆成多个chunk按需加载减少首屏体积”后者答“依赖ES6模块的静态结构在编译阶段就能确定哪些export没有被使用从而在打包时删除”。还有一类跟业务场景强相关的工程化题目比如“音乐App首屏加载慢你怎么优化”。这种题考察的就不只是构建工具本身了而是性能优化的整体思路。我之前整理过一个答题框架资源压缩Gzip、图片格式、缓存策略HTTP缓存、CDN、代码分割路由懒加载、渲染优化SSR、骨架屏。用这个框架去答逻辑清晰不容易漏点。4. 编程题与算法题笔试中的分水岭编程题是TME笔试I里单题分值最高的部分通常有两到三道难度从“基础”到“中等偏上”不等。算法题考察的不是竞赛级别的算法能力而是基本的数据结构运用和编码能力。但别小看它每年栽在编程题上的人不比栽在选择题上的少。4.1 高频算法题类型字符串、数组、递归根据近年大厂前端笔试题的统计前端岗位的算法题集中在三类字符串处理、数组操作、递归与动态规划。TME的编程题由于业务偏向音乐播放器还可能出现跟播放列表、搜索推荐相关的题目背景但核心算法依然是通用类型。字符串处理的代表题是“大数相加”。给定两个字符串形式的非负整数num1和num2计算它们的和并以字符串形式返回。这题的考点有两个一是不能用BigInt偷懒二是要考虑进位边界。function addStrings(num1, num2) { let i num1.length - 1 let j num2.length - 1 let carry 0 let res [] while (i 0 || j 0 || carry) { const n1 i 0 ? Number(num1[i]) : 0 const n2 j 0 ? Number(num2[j]) : 0 const sum n1 n2 carry res.unshift(sum % 10) carry Math.floor(sum / 10) i-- j-- } return res.join() }数组操作的经典题是“数组扁平化并去重排序”。这道题如果写递归代码是function flatten(arr) { return arr.reduce((pre, cur) { return pre.concat(Array.isArray(cur) ? flatten(cur) : cur) }, []) }如果要求用非递归实现可以借助栈function flattenByStack(arr) { const stack [...arr] const result [] while (stack.length) { const item stack.shift() if (Array.isArray(item)) { stack.unshift(...item) } else { result.push(item) } } return result }递归与动态规划在TME笔试中出现的代表题是“爬楼梯”变体一次可以爬1步或2步爬上n阶台阶有多少种方式。核心是f(n) f(n-1) f(n-2)用滚动数组优化空间复杂度笔试时写出递推式不算完还得把环结构写出来。但更常见的是升级版——带成本的爬楼梯或者跳台阶时不能连续跳2步这些变体考的是你能不能举一反三。4.2 编程题如何拿满分边界条件与时间复杂度的双重要求编程题评分通常是“部分用例通过给部分分”所以目标不是“AC全对”而是“尽量多过用例”。根据我帮人复盘笔试的经验以下三个步骤可以帮助你稳定拿分。第一步先写暴力解确保不空题。即使时间复杂度差一点过了基础用例就能拿不少分。第二步再考虑优化。如果暴力解超时再想优化方案。第三步也是很多人忽略的写代码前先列测试用例特别是边界用例。比如数组为空、字符串超长、数值为0、递归深度大等场景。举个例子题目要求“实现一个函数输入一个字符串输出字符出现次数最多的字符”。如果你直接写一个对象统计然后遍历基本用例都能过。但如果题目追加了“如果出现次数相同输出最早出现的字符”很多人没注意到“最早”这个条件在比较时用了严格大于而不是大于等于就会挂掉一半用例。4.3 笔试环境与代码调试技巧TME的笔试一般在牛客网或者赛码网进行这两个平台的前端编程题环境都支持JavaScript和Node.js。有几点需要提前适应编程题的输入输出用readline处理而不是浏览器环境里的prompt。很多第一次参加笔试的人会在这里浪费很多时间。牛客网默认的JS模板是V8引擎的用readline读取输入行后print或console.log输出结果。题目的“运行”按钮只验证示例用例真正提交后在后台会有很多隐藏用例所以测试时多造几组特殊数据。一个实用的调试技巧如果你不确定当前环境是否支持某个API在代码开头先输出该API的类型比如console.log(typeof Promise)看环境里Promise是否可用。这虽然看起来傻但在陌生的在线OJ环境里很管用。5. 实战应试策略时间分配与做题顺序笔试不仅考知识储备也考应试策略。时间分配不合理很可能导致后面的编程题没时间写。我根据TME笔试I常见的“选择题60分钟 简答题20分钟 编程题40分钟”结构整理了一套比较稳妥的时间分配方案。5.1 做题顺序先做编程题还是先做选择题我的建议是先快速做完选择题中送分的基础题然后直接跳到编程题最后再回头啃选择填空里的难题。原因是编程题的分值密度更高一道编程题可能顶五六道选择题而且编程题需要更长的思考时间放在后面容易因为时间压力导致思路混乱。具体节奏可以这样安排前10分钟快速浏览全部题目标注出送分题和难题接下来15分钟做完简单的选择题能一眼看出答案的再花35到40分钟做编程题每道题先保证写出暴力解再尝试优化剩余时间回头攻选择填空里的难题能做就做不能做就凭经验猜选择题的猜题也有技巧。前端笔试的选项通常是四个如果一道题你完全不会可以先排除掉明显不合理的选项再结合“出题人喜欢设置的陷阱”来判断。比如问“以下哪项不属于Vue的构成部分”答案通常是那个你没见过的选项问“以下哪个API不是ES6新增的”答案是那个ES5就有的Object.create。5.2 常见失分点与避坑经验每年校招笔试我陆续收集了不少同学回传的题目反馈总结出几个常见的失分点你复习的时候要特别留意。第一个失分点选择题里的代码题只看不运行。有些选择题给出一段代码让你判断输出很多人只看了一遍就直接选了。正确做法是能运行的题在脑子里像机器一样逐行运行一遍。尤其是循环嵌套、递归调用、原型链查找这类代码只看不run特别容易掉坑。第二个失分点简答题写得太短。简答题的要求通常是“简述XXX的原理”建议写成“定义 关键点 例子”三段式。比如问Vue的虚拟DOM是什么不要只回答“一种用JS对象描述真实DOM结构的技术”要加上“通过diff算法比较新旧vnode差异最小化真实DOM操作”和实际场景的例子。写得越完整得分越稳。第三个失分点编程题不写注释、变量命名混乱。笔试平台的评分可能有人工审核环节代码可读性会影响主观分。合理使用nums、target、index等语义化命名在关键逻辑处加中文注释会给人留下好印象。5.3 笔试前一周的冲刺复习清单如果你距离笔试还有一周左右按下面的清单准备性价比最高复习模块具体内容建议用时JS核心概念原型链、闭包、this、事件循环、Promise2天手写代码专项深拷贝、防抖节流、Promise.all、数组去重、函数柯里化1天框架原理Vue响应式、生命周期、组件通信、Vue3新特性1天工程化与网络webpack核心概念、HTTP缓存、跨域方案、HTTPS握手1天算法刷题LeetCode热题100中的简单、中等题重点是字符串、数组、链表的题目2天复习时多写代码、少看视频。看懂了不代表能写出来笔试考的是手写能力。建议每天抽出至少两个小时在牛客网的在线编程环境里练题提前适应笔试平台的输入输出模式。5.4 心态管理与临场应变笔试心态这件事很玄但确实会影响发挥。我见过一些人编程题第一道没写出来心态崩了后面本来会的题也没做对。应对方法是遇到卡壳超过10分钟的题先跳过做后面的。笔试不要求满分只要通过线就行。一般笔试通过线在60分左右所以哪怕有一两道题不会也不影响大局。还可以准备一个自己的“代码模板库”在笔试前十分钟把这些模板默写在草稿纸上如果允许或者记在心里。比如快速幂、二分查找、树的遍历递归版和迭代版、并查集这类经典的算法模板考到就直接套不需要现场重新推理。最后笔试结束后记得复盘。不管考得如何把题目回忆一遍尤其是自己做错的题和没写出来的题。TME这类公司的笔试通常不止一场第一场挂了还有可能收到第二场的邀请或者后续批次还有机会。复盘就是把经验留给下一轮不要因为一次失利就放弃整个招聘季。坦白说前端笔试考察的内容就那么些难的是在有限时间内把你会的都写出来。我见过不少基础扎实但笔试翻车的同学问题基本都出在时间分配和临场心态上。拿到真题之后好好练手把这篇提到的考点过一遍通过笔试不会太难。
返回列表