如何更简洁地从事件数组计算用户会话时长?
计算用户总会话时长的简洁实现
给定包含登录/登出事件的数组,每个事件包含action(可选值login/logout)和timestamp属性,需计算所有登录与对应登出的时间差总和,已知登录操作始终在对应登出之前。
示例事件数组:
const events = [ { action: 'login', timestamp: 10 }, { action: 'logout', timestamp: 20 }, { action: 'login', timestamp: 55 }, { action: 'logout', timestamp: 65 }, ]
现有实现通过额外变量追踪上次登录时间,可正常运行但不够简洁:
function getUserSessionLength(events) { let userSession = 0 let lastTimeLogIn = 0 for (const { action, timestamp } of events) { if (action === 'login') lastTimeLogIn = timestamp else userSession += timestamp - lastTimeLogIn } return userSession }
方案1:利用Array.reduce实现无外部变量的函数式写法
通过reduce的累加器封装总时长和上次登录时间,无需额外声明外部变量:
function getUserSessionLength(events) { return events.reduce((acc, { action, timestamp }) => { if (action === 'login') { acc.lastLogin = timestamp; } else { acc.total += timestamp - acc.lastLogin; } return acc; }, { total: 0, lastLogin: 0 }).total; }
方案2:基于事件成对特性的极简遍历
由于登录和登出是严格成对出现的,可直接按步长2遍历数组,每组取登出时间减登录时间累加:
function getUserSessionLength(events) { let total = 0; for (let i = 0; i < events.length; i += 2) { total += events[i + 1].timestamp - events[i].timestamp; } return total; }
两种方案均能得到正确结果:对于示例数组,计算结果为(20-10)+(65-55)=20。
内容的提问来源于stack exchange,提问作者Joji
相关产品推荐
相关产品推荐

