我是一个有两年工作经验的前端,最近因为突然发生一些事情离职了,不巧现在是求职寒冬期,很多单位处于暂停招聘状态,我资历平凡、技术一般,找工作困难重重、但我不想放弃,为了避免熊瞎子掰苞米,特此发文记录一下找工作被问及的一些问题
这一部分记不清具体哪天面试的,暂且记录在一起
1、flex布局问题
align-items:flex子项们相对于flex容器在垂直方向上的对齐方式、单行时候垂直居中使用align-items: center
justify-content:水平布局
默认值: flex-start;项目向水平方向的起点对齐
水平方向的终点对齐:flex-end
居中:center
2、js中如何判断对象是否为空
(1)for...in...循环:返回true说明不为空;返回false为空
(2)把json对象转换成json字符串:判断json字符串是否=={}(转换方法:JSON.stringify)
(3) jQuery的EmptyObject()方法
3、js数组去重
(1)借助ES6提供的Set结构 new Set()
var arr = [1,9,8,8,7,2,5,3,3,3,2,3,1,4,5,444,55,22];
var newArr = [...new Set(arr)];
(2)利用 filter() 搭配indeOf()去重
filter() 方法创建一个新的数组,新数组中的元素是通过检查指定数组中符合条件的所有元素。 item是当前元素的值,index是当前元素的索引值。indexOf() 方法可返回某个指定的字符串值在 字符串中首次出现的位置。利用indexOf() 查询到数组的下标,看是否等于当前的下标,相等的 话 就返回,否则不返回值。
var arr = ['apple','apps','pear','apple','orange','apps'];
console.log(arr)
var newArr = arr.filter(function(item,index){
return arr.indexOf(item) === index; // 因为indexOf 只能查找到第一个
});
console.log(newArr);
(3) 利用for 循环 搭配 indexOf 去重
var arr = [1,9,8,8,7,2,5,3,3,3,2,3,1,4,5,444,55,22];
function noRepeat(arr) {
//定义一个新的临时数组
var newArr=[];
//遍历当前数组
for(var i=0;i<arr.length;i++) {
//如果当前数组的第i已经保存进了临时数组,那么跳过,
//否则把当前项push到临时数组里面
if(newArr.indexOf(arr[i]) === -1) { //indexOf() 判断数组中有没有字符串值,如果没有则返回 -1
newArr.push(arr[i]);
}
}
return newArr
}
var arr2 = noRepeat(arr);
(4)利用双重for循环法一:
var arr = [1,9,8,8,7,2,5,3,3,3,2,3,1,4,5,444,55,22];
console.log(arr);
function noRepeat(arr) {
for(var i = 0; i < arr.length-1; i++){
for(var j = i+1; j < arr.length; j++){
if(arr[i]===arr[j]){
arr.splice(j,1);
j--;
}
}
}
return arr;
}
var arr2 = noRepeat(arr);
(5)利用双重for循环法二:
var arr = [1,9,8,8,7,2,5,3,3,3,2,3,1,4,5,444,55,22];
console.log(arr);
function noRepeat(arr){
for (var i = 0; i < arr.length; i++) {
for (var j = 0; j < arr.length; j++) {
if (arr[i] == arr[j] && i != j) { //将后面重复的数删掉
arr.splice(j, 1);
}
}
}
return arr;
}
var arr2 = noRepeat(arr);
(6)借助新数组 通过 indexOf 方法判断当前元素在数组中的索引,如果与循环的下标相等则添加到新数组中
var arr = [1,9,8,8,7,2,5,3,3,3,2,3,1,4,5,444,55,22];
console.log(arr)
function noRepeat(arr) {
var newArr = [];
for (var i = 0; i < arr.length; i++) {
if (arr.indexOf(arr[i]) == i) {
newArr.push(arr[i]);
}
}
return newArr;
}
var arr2 = noRepeat(arr);
(7)利用includes实现数组去重
var arr = [1,9,8,8,7,2,5,3,3,3,2,3,1,4,5,444,55,22];
function noRepeat(arr) {
let newArr = [];
for(i=0; i<arr.length; i++){
if(!newArr.includes(arr[i])){
newArr.push(arr[i])
}
}
return newArr
}
console.log(noRepeat(arr));
(8)forEach方法
forEach循环数组,利用indexOf寻找是否存在重复 不存在就添加进数组 存在则跳过继续寻找
var arr = [1, 1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 3, 2, 3, 3, 2, 2, 1, 23, 1, 23, 2, 3, 2, 3, 2, 3];
var b = distinct(arr);
function distinct(arr) {
result = [],
len = arr.length; //len=29;
arr.forEach(function (v, i, arr) {
var bool = arr.indexOf(v, i + 1);
//从传入参数的下一个索引值开始寻找是否存在重复
if (bool === -1) {
result.push(v);
}
})
return result;
};
console.log(b.toString()); //1,23,2,3
4、数组排序
(1).数组的sort()
默认情况下,sort() 方法将按字母和升序将值作为字符串进行排序。
注意: sort() 方法会改变原始数组。
如果想按照别的顺序进行排序,就必须提供比较函数,该函数要比较两个值,然后返回一个用于说明这两个值的相对顺序的数字。比较函数应该具有两个参数a和b,如果数组中的元素是数值类型,如果需要升序排序,那么就返回a - b;如果需要降序排序,那么就返回b-a;
var oldArr = [19, 55, 6, 52, 4 , 6, 15, 28, 23, 2, 1, 9]
oldArr.sort((a, b) => {
return a-b // 升序
})
console.log(oldArr);
// [1, 2, 4, 6, 6, 9, 15, 19, 23, 28, 52, 55]
(2)冒泡排序
思路:通过两层循环把数组中两两相邻的元素进行比较,比较两个元素的大小,大的元素放后面,从而一步步交换元素的位置,这样最后一个元素是最大值,下一次循环比较就不需要比较这个最大值,持续每次对越来越少的元素重复上面的步骤,直到没有任何一对数字需要比较。
var oldArr = [19, 55, 6, 52, 4 , 6, 15, 28, 23, 2, 1, 9]
function bubbleSort(arr) {
for(let i = 0; i < arr.length; i++) {
for (let j = 0; j < arr.length - i; j++) {
// 如果前一个比后一个大,则交换位置
if (arr[j] > arr[j+1]) {
let temp = arr[j]
arr[j] = arr[j + 1]
arr[j + 1] = temp
}
}
}
return arr
}
console.log(bubbleSort(oldArr));
// [1, 2, 4, 6, 6, 9, 15, 19, 23, 28, 52, 55]
(3)选择排序
第一次从待排序的数据元素中选出最小的一个元素,存放在序列的起始位置,然后再从剩余的未 排序元素中寻找到最小元素,然后放到已排序的序列的末尾。以此类推,直到全部待排序的数据 元素的个数为零。
代码如下:
var oldArr = [19, 55, 6, 52, 4 , 6, 15, 28, 23, 2, 1, 9]
function selectArr(arr) {
for(let i = 0; i < arr.length - 1; i++) {
for(let j = i + 1; j < arr.length; j++) {
if (arr[i] > arr[j]) {
let temp = arr[i]
arr[i] = arr[j]
arr[j] = temp
}
}
}
return arr
}
console.log(selectArr(oldArr));
// [1, 2, 4, 6, 6, 9, 15, 19, 23, 28, 52, 55]
(4)快速排序(二分法排序)
快速排序算法通过多次比较和交换来实现排序,其排序流程如下:
首先设定一个分界值,通过该分界值将数组分成左右两部分。
将大于或等于分界值的数据集中到数组右边,小于分界值的数据集中到数组的左边。此时,左边 部分中各元素都小于分界值,而右边部分中各元素都大于或等于分界值。
然后,左边和右边的数据可以独立排序。对于左侧的数组数据,又可以取一个分界值,将该部分 数据分成左右两部分,同样在左边放置较小值,右边放置较大值。右侧的数组数据也可以做类似 处理。
重复上述过程,可以看出,这是一个递归定义。通过递归将左侧部分排好序后,再递归排好右侧部分的顺序。当左、右两个部分各数据排序完成后,整个数组的排序也就完成了。
var oldArr = [19, 55, 6, 52, 4 , 6, 15, 28, 23, 2, 1, 9]
function quickArr(arr) {
if (arr.length < 1) return arr
var temp = Math.floor(arr.length/2)
var leftArr = [], rightArr = []
var tempNum = arr.splice(temp,1)[0]
for(var i = 0; i < arr.length; i++) {
if (tempNum > arr[i]) {
leftArr.push(arr[i])
}else {
rightArr.push(arr[i])
}
}
return quickArr(leftArr).concat(tempNum, quickArr(rightArr))
}
console.log(quickArr(oldArr));
// [1, 2, 4, 6, 6, 9, 15, 19, 23, 28, 52, 55]
(5)插入排序
插入排序是指在待排序的元素中,假设前面n-1(其中n>=2)个数已经是排好顺序的,现将第n个 数 插到前面已经排好的序列中,然后找到合适自己的位置,使得插入第n个数的这个序列也是排 好顺序的。按照此法对所有元素进行插入,直到整个序列排为有序的过程,称为插入排序
var oldArr = [19, 55, 6, 52, 4 , 6, 15, 28, 23, 2, 1, 9]
function inserArr(arr) {
let newArr = []
for(let i = 0; i < arr.length; i++) {
if (i === 0) {
newArr.push(arr[i])
continue
}
for(j = newArr.length -1; j >= 0; j--) {
if (arr[i] >= newArr[j]) {
newArr.splice(j + 1, 0, arr[i])
break
} else if (j === 0) {
newArr.splice(0, 0, arr[i])
}
}
}
return newArr
}
console.log(inserArr(oldArr));
// [1, 2, 4, 6, 6, 9, 15, 19, 23, 28, 52, 55]
5、BOM对象有哪些
lacation、navigator、screen、histoory
6、vue中key的作用:高效更新虚拟DOM
其原理是vue在patch过程中通过key可以精准判断两个节点是否是同一个,从而避免频繁更新不同元素,使得整个patch过程更加高效,减少DOM操作量,提高性能。另外,若不设置key还可能在列表更新时引发一些隐藏的bug。vue中在使用相同标签名元素的过渡切换时,也会使用到key属性,其目的也是为了让vue可以区分它们,否则vue只会替换其内部属性而不会触发过渡效果。
7、find()方法的作用
find()方法用于查找数组中符合条件的第一个元素,如果没有符合条件的元素,则返回undefined
注:
find() 对于空数组,函数是不会执行的。
find() 并没有改变数组的原始值。
语法:
array.find(function(currentValue, index, arr),thisValue)
callback:必须。为数组中每个元素执行的函数,该函数接受三个参数:
currentValue:必须。数组中正在处理的当前元素。
index:可选。当前元素的索引值。
arr:可选。当前元素所在的数组对象。
thisValue:可选。传递给函数的值一般用 "this" 值。
如果这个参数为空, "undefined" 会传递给 "this" 值
举个例子:
let arr1 = [1, 2, 3, 4, 5];
let num = arr1.find(item => item > 1);
console.log(num) //輸出的結果是
8、findIndex()方法的作用
常用来查找数组中满足条件的第一项元素的下标
举个例子:
const arr = [1, 2, 3, 4, 5, 3, 3, 2, 4, 5 ]
// 可以这么写
let index = arr.findIndex(item => {
return item > 2
})
console.log(index) // 2
// 也可以这么写
let index = arr.findIndex(item => item > 2)
find()和findIndex()区别:
find()返回查找到的元素;findIndex()返回查找到元素的下标
9、forEach和for...in...的区别
forEach只能用于循环数组, forEach里面有个回调函数,回调函数有三个值,每个元素,索引,和数组本身。
for...in...可以用来循环对象,数组,和字符串。key就是代表的键名,obj[key]就是键值。
但是高级方法获取建名键值Object.values(obj)获取键值
Object.keys(obj)获取键名
for...of... 和for...in...的写法是一模一样的,但是for...of...是用来循环键值的,只能用在数组和字符串上。for...in...的key是循环出来的键名
10、vue父组件给子组件传参
props:父组件中把要传递的参数写在子组件标签中、子组件用props:['']获取
ref:在父组件内通过ref获取子组件实例,然后调用子组件方法,并传递相关数据作为参数
$ parent:子组件对父组件进行操作
依赖注入:provide()、inject()
11、vue子组件给父组件传参
$emit、$refs
12、git指令
git clone 地址
git push //强行推送 慎用
git push origin master //推送到master分支
touch a // 创建一个a文件
echo 1234 >> a // 把1234这个内容放入a文件
cat a // 打开a文件 读取出a文件中的内容
mkdir test // 创建test文件夹
rm 文件名 // 删除文件
pwd // 打印当前工作路径
gitk // 用git命令快速打开git GUI
ls // 查看当前路径下面的所有文件名
ls 文件夹名 // 查看对应文件夹中的内容
ls -l // 拉出最近git提交记录以及对应修改的文件名
ls -l -a // 拉出最近git提交记录以及对应修改的文件名,隐藏的文件也会显示
cd ~ // 将工作路径快速切换到root
cd - // 将工作路径切换到上一状态
cd ../ // 切回到上一个工作路径
cd 文件夹名 // 进入某个目录
cd / // 进入根目录
git init // 初始化 在工作路径上创建主分支
git clone 地址 // 克隆远程仓库
git clone -b 分支名 地址 // 克隆分支的代码到本地
git status // 查看状态
git add 文件名 // 将某个文件存入暂存区
git checkout -- file // 撤销工作区的修改 例如git checkout -- readMe.txt 将本次readMe.txt在工作区的修改撤销掉
git add b c //把b和c存入暂存区
git add . // 将所有文件提交到暂存区
git add -p 文件名 // 一个文件分多次提交
git stash -u -k // 提交部分文件内容 到仓库 例如本地有3个文件 a b c 只想提交a b到远程仓库 git add a b 然后 git stash -u -k 再然后git commit -m "备注信息" 然后再push push之后 git stash pop 把之前放入堆栈的c拿出来 继续下一波操作
git commit -m "提交的备注信息" // 提交到仓库
若已经有若干文件放入仓库,再次提交可以不用git add和git commit -m "备注信息" 这2步, 直接用
git commit -am "备注信息" // 将内容放至仓库 也可用git commit -a -m "备注信息"
* git commit中的备注信息尽量完善 养成良好提交习惯 例如 git commit -m "变更(范围):变更的内容"
存储密码凭证 设置别名 获取config信息以及配置git config --list // 获取config信息
git config --global core.safecrlf false // 去掉git add 命令后 出现的一堆CR LF提示信息
其中CR是回车的意思 LF是换行
git config --global user.name"your name" // 设置username
git config --global user.email"your_email@youremail.com" // 设置邮箱
git config --global credential.helper wincred // 存储凭证 (可用于输入一次用户密码后,不再输入 有时我们已经用SSH key 绑定关联好了 但是每次git提交的时候 还是需要你输入用户名密码 在这个时候 敲入这个命令 将凭证存储起来 用户名密码就不需要再次输入了)
git config --global alias.ci commit // 将commit命令设置别名ci git commit命令将由git ci来代替
查看git常用命令:git helper -a
逐行查看文件的修改历史:
git blame 文件名 // 查看该文件的修改历史
git blame -L 100,10 文件名 // 从100行开始,到110行 逐行查看文件的修改历史
清除
git clean -n // 列出打算清除的档案(首先会对工作区的内容进行提示)
git clean -f // 真正的删除
git clean -x -f // 连.gitignore中忽略的档案也删除
git status -sb (sb是 short branch) // 简洁的输出git status中的信息
删除放入暂存区文件的方法(已commit后)
git rm 文件名 // 将该文件从commit后撤回到add后
git reset HEAD^ --hard // 删除后 可以用git rm 文件名再回撤一步
修改文件名以及移动
git mv a b // 把a文件名字改成b 并且直接放入git add后的暂存区
git mv b ./demos/ // 把b文件移动到demos文件夹下
对比工作区,暂存区,仓库的差异
git diff // 查看变更 工作区与暂存区的差异比对
git diff --cached // 暂存区与提交版本的差异
git diff HEAD // 工作区与仓库中最后一次提交版本的差别
git diff 版本哈希值 版本哈希值 // 查看这2个版本哈希之间的区别
或者 git diff HEAD~数字 HEAD~数字
git diff tt 就是倒数第5个版本与第一个版本之间的差异
git diff --cached tt 暂存区与倒数第5个版本之间的比对
查看提交信息
git show HEAD // 查看最后一次提交修改的详细信息 也可以用git show 哈希值 查看对应的内容
git show HEAD^ // 查看倒数第二次的提交修改详细信息
git show HEAD^^ 或者git show HEAD~2 查看前2次变更
git show HEAD 或 git show 哈希值 或者git show tag(标签名) 都可以查看最近一次提交的详细信息
查看信息
git log --pretty=format:'%h %ad | %s%d [%an]' --graph --date=short
// 获取git log里的树形详细信息 包括hasg 日期 提交信息 提交人等
git log --oneline //拉出所有提交信息 q是退出
git log -5 // 查看前5次的提交记录
git log --oneline -5 // 打印出的日志里面只有哈希值和修改的内容备注
git log 文件名 // 查看该文件的提交
git log --grep // 想过滤看到的内容 过滤日志
git log -n // 查看近期提交的n条信息内容
git log -p // 查看详细提交记录
变基操作,改写历史提交 把多次提交合并起来
git rebase -i HEAD~3 变基之后的哈希值与之前的不同 证明变基是重新做的提交 把多次提交合并成了几次提交
回撤操作
git commit --amend -m "提交信息" // 回撤上一次提交并与本次工作区一起提交 git reset HEAD~2 --hard // 回撤2步 git reset --files // 从仓库回撤到暂存区 git reset HEAD // 回撤暂存区内容到工作目录 git reset HEAD --soft 回撤提交到暂存区 git reset HEAD --hard // 回撤提交 放弃变更 (慎用) git reset HEAD^ // 回撤仓库最后一次提交 git reset --soft HEAD^ // 将执行git commit 并没有执行git push到远程仓库的内容 回撤到工作区 并且保存在工作区 git reset --hard HEAD^ // 将执行git commit 并没有执行git push到远程仓库的内容 回撤并且不保存 // 注意 在window电脑端 可能会出现执行git reset --hard HEAD^命令时 提示More? 所以针对windows 我们回撤内容需要键入git reset --hard HEAD^^才可以 如果我们git commit提交2次 想把2次都回撤到工作区保存 可以使用git reset --soft HEAD~2 git reset --hard commitid // 回撤到该次提交id的位置 回撤后本地暂存区可能有内容 本地仓库有要同步的内容 此时 丢弃掉暂存区的内容 并且强制将本地的内容推送至远程仓库 执行下面的命令 git push -u -f origin 分支名 这样就可以完全回撤到提交id的位置 git reset --soft commitid // 回撤到该次提交id的位置 并将回撤内容保存在暂存区 git push -f -u origin 分支名 所有内容都回撤完了 将回撤后的操作强制推送到远程分支 git push origin/分支名 --force 强制将本地回撤后的操作 强制推送到远程分支
标签操作
git tag // 查看列出所有打过的标签名 例如V1.1 V1.11 V1.12 V1.13等
git tag -d 标签名 // 删除对应标签 只是删除了本地的
git push origin :refs/tags/远程标签名 // 删除远程仓库的标签 可以在删除本地标签后 执行这个操作 同步远程
git tag 标签名字 // 在当前仓库打个标签
git tag 标签名 commitid // 给已知提交id的版本打标签 例如git tag v1.1.1 6f8f25fcf57a17e6c72b33f6bca0797fab15ff8b // 给历史提交打V1.1.1的tag标签 这里的commitid可以缩写 缩写成前6位就可以 例如git tag V1.1.1 6f8f25 一样可以给这个提交id打上tag
git tag -l // 过滤tag 例如 git tag -l "V1.1*" // V1.1 V1.11 可以过滤前面是V1.1开头的内容
git show 标签名称 // 查看tag的详细信息 包括commitid 作者信息 日期 内容
git push origin 标签名称 // 同步这个tag到远程服务器 默认tag是打在本地的 这个命令可以把它推到远程
git push origin --tags // 将本地所有tag推送到远程服务器
git pull --tags // 把远程仓库的标签也拉取下来
git tag foo -m "message" // 在当前提交上,打标签foo 并给message信息注释
git tag 标签名 哈希值 -m "message" // 在某个哈希值上打标签并且写上标签的信息
git tag foo HEAD~4 // 在当前提交之前的第4个版本上 打标签foo
git stash // 把暂存区的内容 暂时放在其他中 使暂存区变空
git stash list // 查看stash了哪些存储
git stash pop // 将stash中的内容恢复到当前目录,将缓存堆栈中的对应stash删除
git stash apply // 将stash中的内容恢复到当前目录,不会将缓存堆栈中的对应stash删除
git stash clear // 删除所有缓存的stash
git reset --hard // 回撤git stash pop的内容
分支
git branch 分支名 // 新建分支
git branch // 查看当前所有分支
git checkout 分支名 // 检出分支
git checkout -b 分支名 // 创建并切换分支
git checkout commitId 文件名(文件路径下的文件名) 还原这个文件到对应的commitId的版本
(例如src/page/attendance/attendanceSum.vue我想把它还原到2个版本之前 首先git log src/page/attendance/attendanceSum.vue找到对应想要还原的版本
复制版本提交的commitID 然后执行git checkout commitID src/page/attendance/attendanceSum.vue
这样就把attendanceSum.vue这个单个文件 还原到了对应版本)
git branch -v // 查看分支以及提交hash值和commit信息
git merge 分支名 // 把该分支的内容合并到现有分支上
git cherry-pick commitId // 把其他分支的某一次提交内容合并到当前分支 这个在我们平时多分支开发中很常用
git branch -d 分支名 // 删除分支
git branch -D 分支名 // 强制删除 若没有其他分支合并就删除 d会提示 D不会
git branch -m 旧分支名 新分支名 // 修改分支名
git branch -M 旧分支名 新分支名 // 修改分支名 M强制修改 若与其他分支有冲突也会创建(慎用)
git branch -r // 列出远程分支(远程所有分支名)
git branch -a // 查看远程分支(列出远程分支以及本地分支名 远程分支会以remote/origin/分支名这种形式展示 红色标识)
git branch // 查看本地分支
git reflog show --date=iso <branch name> // 查看分支创建时间 例如git reflog show --date=iso origin/feature-PCDEC-6375 输出 88e22885 (HEAD -> feature-PCDEC-6375, origin/feature-PCDEC-6375, origin/EC-master, EC-master) refs/remotes/origin/feature-PCDEC-6375@{2021-07-27 11:31:23 +0800}: fetch: storing head 创建时间就是2021-07-27 11:31:23
git fetch // 更新remote索引
git push -u origin 分支名 // 将本地分支推送到origin主机,同时指定origin为默认主机,后面就可以不加任何参数使用git push 也可解决 git建立远程分支关联时出现fatal ... upstram的问题
git push origin --delete 分支名 (将git branch -D 分支名 删掉的分支 同步到远程主机 将origin/分支名的该分支也删除掉)
git remote show origin 查看remote地址,远程分支,还有本地分支与之相对应关系等信息(结合git branch -a使用)
git remote prune origin 删除远程仓库不存在的分支 (git branch -a使用)
git reflog show --date=iso 分支名 // 查看指定分支的创建时间 以及更改记录等
git仓库迁移
// 首先在当前项目主分支先执行git pull 把代码更新为最新
git remote set-url origin <新的仓库名>
git push -u -f origin
git push -u -f origin --all // 把所有分支迁移过去
git push -u -f origin --tags // 把所有tag迁移过去
// 然后去拉取新的仓库代码就可以了 如果新仓库之前拉取过了
重新仓库迁移 里面分支没同步的话 执行 git fetch试一下 同步过来
5006

被折叠的 条评论
为什么被折叠?



