前端妹子失业在家刷题,开发了个leetcode刷题工具,效率直接翻倍!

大家好,我是薇薇,一名沪漂女程序员,年前惨遭被裁,正值在家悲伤抠脚之际,突然看到两位朋友在合谋开发一款刷leetcode的小工具------leetcode-practice......

下面重点稍微来介绍一下

朋友A:Angular的忠实信徒,插件的主创+仓库创建人

朋友S:n年(n>=5)前端经验的神秘大佬,有钱有闲热爱开源

在神秘力量的号召下~~(主要是A太热情了,把我拉了项目,实在不好意思挂名贡献者却啥也不干)~~,从一开始的摆烂抠脚到参与进来,现在这款工具也初具雏形

关于详细的介绍参见A佬写的这篇# [leetcode-practice]一款能够适合骑驴找马程序员的摸鱼神器

快速开始

leetcode-practice拥有多种形态,但是我更倾向于脱离仓库本身的使用方式,也就是说你可以尝试在终端内执行(node版本大于20)

这样做的好处主要是你可以自己脱离leetcode-practice项目建立自己的git题库,方便回顾。

npm install -g leetcode-practice

比如说你想刷这道题

那么可以执行一下

perl 复制代码
lc 1

或者

css 复制代码
lc -i 1

这时候当前目录会出现一个文件夹

description是题目的markdown格式的描述,当然index.js的注释中也可以看到题目描述,但是markdown可以更方便的查看图片,这里推荐下载一个markdown preview 插件

index.js的内容如下

ini 复制代码
/**
 * 1.两数之和 
 * 给定一个整数数组 nums 和一个整数目标值 target,请你在该数组中找出 和为目标值 target  的那 两个 整数,并返回它们的数组下标。
 * 你可以假设每种输入只会对应一个答案。但是,数组中同一个元素在答案里不能重复出现。
 * 你可以按任意顺序返回答案。
 *  
 * 示例 1:
 * 输入:nums = [2,7,11,15], target = 9
 * 输出:[0,1]
 * 解释:因为 nums[0] + nums[1] == 9 ,返回 [0, 1] 。
 * 示例 2:
 * 输入:nums = [3,2,4], target = 6
 * 输出:[1,2]
 * 示例 3:
 * 输入:nums = [3,3], target = 6
 * 输出:[0,1]
 *  
 * 提示:
 *  2 <= nums.length <= 104
 *  -109 <= nums[i] <= 109
 *  -109 <= target <= 109
 *  只会存在一个有效答案
 *  
 * 进阶:你可以想出一个时间复杂度小于 O(n2) 的算法吗?
 * 
 */
/**
 * @param {number[]} nums
 * @param {number} target
 * @return {number[]}
 */
var twoSum = function(nums, target) {
// 题解需要自己填入哦
    const map = new Map();
    for(let i =0, len = nums.length; i< len; i++) {
        if(map.has(target - nums[i])) {
            return [map.get(target - nums[i]), i]
        }
        map.set(nums[i], i);
    }
};

/**
 * Test case
 */
showLogs(
    twoSum,
    {
        data: [[ [2,7,11,15],  9],[ [3,2,4],  6],[ [3,3],  6]],
        structure: ["number[]","number"],
    },
    {
        data: [[0,1],[1,2],[0,1]],
        structure: ["number[]"]
    }
)
console.log('点击跳转到题目提交:https://leetcode.cn/problems/two-sum/');

这时候就可以愉快的使用vscode的代码提示和调试功能了,同时你还可以在本地建立自己的刷题仓库,方便回顾和查看~

leetcode-practice支持本地验证结果 执行

lk 1

或者

css 复制代码
lk -i 1

下面简单介绍一下我贡献的部分吧

数据结构转换

leetcode提供的测试用例不管是链表、树还是图都是以数组形式,我解析了leetcode提供的js code的js doc,并这些数据结构写了两个转换函数,toArray 链表/树/图转换为数组,parse 将数组解析为链表/树/图 以链表为例

javascript 复制代码
/**
 * ListNode 链表数据结构
 * @param val
 * @param next
 * @constructor
 */

export class ListNode {
  constructor(val, next) {
    this.val = (val === undefined ? 0 : val);
    this.next = (next === undefined ? null : next);
  }

  static parse(arr) {
    if (arr.length === 0) {
      return null; // Return null for an empty array
    }
    const head = new ListNode(arr.shift(), null);
    let current = head;
    while (arr.length > 0) {
      current.next = new ListNode(arr.shift(), null);
      current = current.next;
    }
    return head;
  }

  static toArray(listNodes, arr = []) {
    if (listNodes === undefined || listNodes === null) {
      return arr;
    }

    arr.push(listNodes.val);
    return ListNode.toArray(listNodes.next, arr);
  }
}

单元测试

忘记哪位大佬说,成熟的开源项目,测试用例覆盖率一定很高,虽然这个项目还处于起步状态,我还是为它添加了单元测试。 这里选型了vitest,开箱即用,非常方便,强烈推荐

image.png

lc/lk命令

这一部分也是研究了一番vue-cli得出来的结论,在package.json中有一个bin的字段,起到命令到本地的映射作用,使用npm link就可以将进行调试了

顺便一提,打开全局的npm安装目录可以看到

没错,lc,lf,lk在这里呢

测试用例的执行

你一定很疑惑,index.js中showLogs并没有提供上下文,那么执行lk 1的时候是怎样提供测试用例的验证的呢?

运行时执行代码,大家肯定都能想到js中的著名黑魔法------eval或者new Function,没错,第一版我就是简单用eval来实现的,但是这样做肯定既不优雅也不安全......

这里要讲一个小插曲,这不是我正失业在家边emo边惆怅未来该怎么办嘛,人在这种时候脆弱的时候,就容易想到那些斯人已逝的前辈,于是我就去翻司徒正美大佬的知乎,发现了他生前写的最后一篇文章# nodejs虚拟机,也为我提供了灵感,有一种冥冥之中收到前辈指引的感觉,感谢司徒正美大佬无私的贡献与分享,让前端得以薪火相传!

简单来说......

nodejs有一个叫vm的模块,可以用来执行代码块和执行上下文(比如说浏览器中的window对象,在node中就是通过这个模块提供的,这也是import的底层实现),它提供了一个沙箱,让代码得以安全的执行。

这里放上核心代码

javascript 复制代码
export function executeScript(filePath, context) {
    const fileContent = fs.readFileSync(filePath, 'utf-8');
    const script = new vm.Script(fileContent);
    return script.runInContext(context);
}

/**
 * 执行问题检测进程
 * @param path
 */
export const checkQuestion = async (path)=>{
    return await executeScript(path, vm.createContext({
        showLogs,console
    }))
}

好了,有关leetcode-practice的技术揭秘就写到这里吧,下一步我们会继续完善这个工具,也许会有vscode插件或者更多功能(比如说难产中的lf)

我的想法是想做一键拉hot 100到本地,主要是为了满足自己的需求,毕竟我真的失业了在找工作呀,如果有一起在家抠脚的小伙伴想加入我们,欢迎加入相亲交友网站github一起开发~或者给我们的仓库点点star也行呀

⭐ 👉仓库地址

相关推荐
Zheng1131 小时前
【可视化大屏】将柱状图引入到html页面中
javascript·ajax·html
john_hjy1 小时前
【无标题】
javascript
软件开发技术深度爱好者2 小时前
用HTML5+CSS+JavaScript庆祝国庆
javascript·css·html5
汪子熙2 小时前
Angular 服务器端应用 ng-state tag 的作用介绍
前端·javascript·angular.js
昨天;明天。今天。8 小时前
案例-表白墙简单实现
前端·javascript·css
安冬的码畜日常8 小时前
【玩转 JS 函数式编程_006】2.2 小试牛刀:用函数式编程(FP)实现事件只触发一次
开发语言·前端·javascript·函数式编程·tdd·fp·jasmine
小御姐@stella8 小时前
Vue 之组件插槽Slot用法(组件间通信一种方式)
前端·javascript·vue.js
GISer_Jing8 小时前
【React】增量传输与渲染
前端·javascript·面试
GISer_Jing8 小时前
WebGL在低配置电脑的应用
javascript
万叶学编程11 小时前
Day02-JavaScript-Vue
前端·javascript·vue.js