| 属性 | 解释 | 取值(*默认) | 备注 | |
|---|---|---|---|---|
| 容器 | flex-direction | 主轴方向 | *row | row-reverse | column | column-reverse | |
| flex-wrap | 轴线上换行 | *nowrap | wrap | wrap-reverse | 如果一条轴线排不下,如何换行 | |
| justify-content | 主轴上的对齐 | *flex-start | flex-end | center | space-between | space-around | ||
| align-items | 交叉轴上的对齐 | flex-start | flex-end | center | baseline | *stretch | ||
| align-content | 多根轴线时在交叉轴的对齐方式 | flex-start | flex-end | center | space-between | space-around | *stretch | 如果项目只有一根轴线,该属性不起作用 | |
| flex-flow | = flex-direction flex-wrap | *[row nowrap] | ||
| 项目 | flex-grow | 项目的放大比例 | *0 (即如果存在剩余空间,也不放大) | 如果所有项目的flex-grow属性都为1,则它们将等分剩余空间(如果有的话)。如果一个项目的flex-grow属性为2,其他项目都为1,则前者占据的剩余空间将比其他项多一倍 |
| flex-shrink | 项目的缩小比例 | *1 (如果空间不足,该项目将缩小) | 如果所有项目的flex-shrink属性都为1,当空间不足时,都将等比例缩小。如果一个项目的flex-shrink属性为0,其他项目都为1,则空间不足时,前者不缩小。负值对该属性无效 | |
| flex-basis | 在分配多余空间之前,项目占据的 主轴空间(main size) |
*auto (即项目的本来大小) | 浏览器根据这个属性,计算主轴是否有多余空间(它可以设为跟width或height属性一样的值(比如350px),则项目将占据固定空间) | |
| align-self | 单个项目有与其他项目不一样的对齐方式 | *auto | flex-start | flex-end | center | baseline | stretch | 默认值为auto,表示继承父元素的align-items属性,如果没有父元素,则等同于stretch | |
| order | 排序 | *0 | 数值越小排列越前 | |
| flex | = flex-grow flex-shrink flex-basis | *[0 1 auto] 快捷值auto=1 1 auto 快捷值none=0 0 auto |
后两个属性可选 |
// 发送消息端
window.parent.postMessage('message', 'http://test.com')
// 接收消息端
var mc = new MessageChannel()
mc.addEventListener('message', event => {
var origin = event.origin || event.originalEvent.origin
if (origin === 'http://test.com') {
console.log('验证通过')
}
})
UDP是非面向连接协议,使用udp协议通讯并不需要建立连接,它只负责把数据尽可能发送出去,并不可靠,在接收端,UDP把每个消息断放入队列中,接收端程序从队列中读取数据。
socket是一组实现TCP/UDP通信的接口API
socket连接过程的三个步骤
socket连接一旦建立就保持连接状态,而HTTP连接则不一样,它基于tcp协议的短连接,也就是客户端发起请求,服务器响应请求之后,连接就会自动断开,不会一直保持。
否则(包括添加了用户凭证的)为preflightedRequest,先发options请求预检,得到响应再发请求
1xx: 信息,服务器收到请求,需要请求者继续执行操作
回收机:垃圾回收器周期性找出无用变量,释放
管理内存:解除引用
function create(name,age,job){
var o= new Object();
o.name = name;
o.age = age;
o.job = job;
o.say = function(){};
return o;
}
var person = create('sdf', 15, 'sdf');
问题:不能识别对象类型
function Person(name, age, job){
this.name = name;
this.age = age;
this.job = job;
this.say = function(){};
}
var person = new Person('sdf', 67, 'sdf');
问题:不能共享公共方法
function Person(){}
Person.prototype = {
custructor: Person,
name: 'a',
arr: [1, 2]
}
var person = new Person();
问题:属性值为引用类型的时候,实例们会共享
function Person(name, age){
this.name = name;
this.age = age;
this.arr = [1, 2];
}
Person.prototype = {
custructor: Person,
say: function(){}
}
var person = new Person('sdf', 46);
function Person(name, age){
this.name = name;
this.age = age;
if(typeof this.say != 'function'){
Person.prototype.say = function(){};
}
}
var person = new Person('sdf', 46);
function Person(name,age,job){
var o= new Object();
o.name = name;
o.age = age;
o.job = job;
o.say = function(){};
return o;
}
var person = new Person('sdf', 15, 'sdf');
function Person(name,age,job){
var o= new Object();
o.say = function(){ alert(name); };
return o;
}
var person = new Person('sdf', 15, 'sdf');
class Watcher {
// name模拟使用属性的地方
constructor(name, cb) {
this.name = name
this.cb = cb
}
update() {//更新
console.log(this.name + "更新了");
this.cb() //做出更新回调
}
}
class Dep {//依赖收集器
constructor() {
this.subs = []
}
addSubs(watcher) {
this.subs.push(watcher)
}
notify() {//通知每一个观察者做出更新
this.subs.forEach(w => {
w.update()
});
}
}
// 假如现在用到age的有三个地方
var w1 = new Watcher("我{{age}}了", () => { console.log("更新age"); })
var w2 = new Watcher("v-model:age", () => { console.log("更新age"); })
var w3 = new Watcher("I am {{age}} years old", () => { console.log("更新age"); })
var dep = new Dep()
dep.addSubs(w1)
dep.addSubs(w2)
dep.addSubs(w3)
// 在Object.defineProperty 中的 set中运行
dep.notify()
class Son3 extends Father {
constructor(y) {
super(200);
this.y = y;
}
}
function SuperType(){ this.property = true; }
SuperType.prototype.getSuperValue = function(){ return this.property; };
function SubType(){ this.subproperty = false; }
SubType.prototype = new SuperType();
SubType.prototype.getSubValue = function(){ return this.subProperty; };
var instance = new SubType();
问题:属性值为引用类型的时候,实例们会共享;不能传参
function SuperType(a){ this.name = a; }
function SubType(){
SuperType.call(this, 'b');
this.c = 'c';
}
var instance = new SubType();
问题:不能共享公共方法
function SuperType(a){
this.a = a;
this.arr = [1, 2];
}
SuperType.prototype.say = function(){ return this.a; };
function SubType(a,b){
SuperType.call(this, a);
this.b = b;
}
SubType.prototype = new SuperType();
SubType.prototype.constructor = SubType;
SubType.prototype.say2 = function(){};
var instance = new SubType('a', 'b');
问题:调用两次超类的构造函数;子类上存在父类上所有的不必要的属性
function object(o){
function F(){}
F.prototype = o;
return new F();
}
var b = object({a: 1});
function createAnother(o){
var clone = object(o);
clone.say = function(){};
return clone;
}
var b = createAnother({a: 1});
function SuperType(a){
this.a = a;
this.arr = [1, 2];
}
SuperType.prototype.say = function(){ return this.a; };
function SubType(a,b){
SuperType.call(this, a);
this.b = b;
}
SubType.prototype = Object.create(SuperType.prototype);
SubType.constructor = SubType
解决:在一个函数内部访问另一个函数内部的变量
本质:本质就是在一个函数内部创建另一个函数
计算机语言可以分为两种:编译型和解释型语言。编译型语言经过编译器编译后保留机器能读懂的二进制文件,比如 C/C++,go 语言。
解释型语言是在程序运行时通过解释器对程序进行动态解释和执行,比如 Python,JavaScript 语言。
编译型语言的编译过程:编译器首先将代码进行词法分析、语法分析,生成抽象语法树(AST),然后优化代码,最后生成处理器能够理解的机器码;
解释型语言解释过程:解释器会对代码进行词法分析、语法分析,并生产抽象语法树(AST),不过它会再基于抽象语法树生成字节码,最后根据字节码执行程序;
AST 的生成:第一阶段是分词(词法分析),将一行行源码拆解成一个个 token(语法上不可再分、最小单个字符)。
第二阶段是解析(语法分析),将上一步生成的 token 数据,根据语法规则转为 AST,这一阶段会检查语法错误;
字节码存在的意义:直接将 AST 转化为机器码,执行效率是非常高,但是消耗大量内存,从而先转化为字节码解决内存问题;
解释器 ignition 在解释执行字节码,同时会手机代码信息,发现某一部分代码是热点代码(HotSpot),编译器把热点的字节码转化为机器码,并保存起来,下次使用;
字节码配合解释器和编译器的计数实现称为即时编译(JIT)
// 斐波那契数列:1、1、2、3、5、8、13、21、34、……
function result(n){
if(n==1||n==2){
return 1
};
return result(n-2)+result(n-1);
}
项目中遇到过什么问题:
离职原因:换个环境
自己最大的弱点:代码细节
你的亮点在哪里:克服困难,守时上班
加班:我现在已经成家,生活上已经稳定,这样更能全身心的投入工作。但同时,我也会提高工作效率,减少不必要的加班。
开发流程/前后端合作方式/分组还是分项目
工作任务/前端开发环境/开发语言/技术栈
工作内容
职位内容
部门的组织架构/向谁汇报,直接上司的职位是,我所工作的部门有多少人
公司对这个职位有什么要求/未来的发展状况/对员工生涯规划
对此职位一般如何作绩效考核
工资构成大概什么情况:
社保/基数
多少薪/股票期权
作息:day,week,加班
试用期时间/80%
工作居住证
停车
当一个Vue实例创建时,vue会遍历data选项的属性,用 Object.defineProperty 将它们转为 getter/setter并且在内部追踪相关依赖,在属性被访问和修改时通知变化。
每个组件实例都有相应的 watcher 程序实例,它会在组件渲染的过程中把属性记录为依赖,之后当依赖项的 setter 被调用时,会通知 watcher 重新计算,从而致使它关联的组件得以更新。
createStore(reducer, [preloadedState], 中间件)
方法:
const store = createStore(
reducer,
compose(
applyMiddleware(thunk),
DevTools.instrument()
)
)
const mapStateToProps = store => ({ state: store.state })
const mapDispatchToProps = dispatch => ({ actions: state => dispatch(actionCreators(state)) })
connect( mapStateToProps, mapDispatchToProps )(TodoList);
import { combineReducers } from 'redux'
const reducer = combineReducers({
a: doSomethingWithA,
b: processB,
c: c
})
1. $ npm install vue
2. 指令(Directives):
v-bind:title = "" :title="" //dom attribute
v-bind:[attrname]=""
<my-component v-for="(item, index) in items" v-bind:key="item.id"
v-bind:itemdata="item"
v-bind:itemindex="index"></my-component> //传入组件数据
v-on:click="" @click="" //dom 事件绑定
v-on:[eventname]="">
v-if="" v-else-if v-else //dom 结构 分支2
v-for="item in []" //dom 结构 循环
v-for="(item, index) in []"
v-for="item of []"
v-for="value in {}"
v-for="(value, name) in {}"
v-for="(value, name, index) in {}"
v-for="n in 10" //重复10次
v-for="item in []" v-bind:key="item.id" //2.2.0+: 当在组件上使用v-for时,key是必须的
v-model=""
v-once
v-html=""
v-show="" //不支持<template>元素,也不支持 v-else
3. 组件:
Vue.component('component-tag', {
data: function () { //data 必须是一个函数
return {
count: 0
}
},
template: '',
computed: {},
watch: {},
methods: {},
生命周期钩子: function(){}
})
4. Vue实例:
var vm = new Vue({
el: '#components-demo'
})
vm.$data
vm.$el
vm.$watch
5. 通过 Prop 向子组件传递数据
Vue.component('blog-post', {
props: ['title'],
template: '<h3>{{ title }}</h3>'
})
<blog-post title="sdf"></blog-post>
<blog-post title="bbb"></blog-post>
<blog-post v-for="post in posts" v-bind:key="post.id" v-bind:title="post.title"></blog-post>
5. 监听子组件事件
<blog-post v-on:enlarge-text="postFontSize += 0.1"></blog-post>
子组件内:
<button v-on:click="$emit('enlarge-text')">btn</button>
<blog-post v-on:enlarge-text="postFontSize += $event"></blog-post>
<button v-on:click="$emit('enlarge-text', 0.1)">btn</button>
<blog-post v-on:enlarge-text="onEnlargeText"></blog-post>
methods: {
onEnlargeText: function (enlargeAmount) {
this.postFontSize += enlargeAmount
}
}
5. 生命周期钩子
6. Class&Style
v-bind:class="{active:false, 'text-err':true}"
v-bind:class="['bb', {active:true, 'text-err':false}]"
v-bind:style="{color:activeColor, fontSize:fontSize+'px', 'text-align':'center'}"
v-bind:style="[baseStyles, overridingStyles]"
v-bind:style="{display: ['-webkit-box', '-ms-flexbox', 'flex']}"
7.
<template v-if="true">
<label>a</label>
<input key="akey">
</template>
<template v-else>
<label>b</label>
<input key="bkey">
</template>
<template v-for="item in []">
<li>{{ item.msg }}</li>
<li class="divider" role="presentation"></li>
</template>
8. 数组更新检测
Vue可以检测数组的变动 push() pop() shift() unshift() splice() sort() reverse()
不能检测数组的变动: vm.items[3] = 5 vm.items.length = 2
(解决:在响应式系统内触发状态更新)
Vue.set(vm.items, 3, 5)
vm.items.splice(3, 1, 5)
vm.$set(vm.items, 3, 5)
vm.items.splice(newLength)
9. 对象变更检测
不能检测对象属性的添加或删除:
var vm = new Vue({data: {a: 1}});
vm.a = 2 //响应
vm.b = 2 //不响应
(解决:)
Vue.set(vm.user, 'age', 27)
vm.$set(vm.user, 'age', 27)
不要Object.assign(vm.user, {age:27, anothor:'add'})
而要vm.user = Object.assign({}, vm.user, {age:27, anothor: 'add'})
10. 事件
事件处理方法:
v-on:click="counter += 1"
v-on:click="method1"
new Vue({
methods: {
method1: function(event){ alert(event.target.tagName) }
}
})
v-on:click="method2('a', $event)"
new Vue({
methods: {
method2: function(msg,event){ alert(event.target.tagName) }
}
})
事件修饰符:
v-on:click.stop="" //阻止单击事件继续传播
v-on:submit.prevent="" //提交事件不再重载页面
v-on:click.stop.prevent //只有修饰符
v-on:click.capture="" //使用事件捕获模式
v-on:click.self="" //当前元素是自身时触发(即事件不是从内部元素触发的)
v-on:click.once="" //只会触发一次
v-on:scroll.passive="" //不会等待`scroll`完成
v-on:keyup.enter="" enter tab delete(删除和退格) esc space up down left right
v-on:keyup.page-down=""
v-on:keyup.13=""
v-on:keyup.alt.67="" ctrl alt shift meta
v-on:click.ctrl="" //即使Alt或Shift被一同按下时也会触发
v-on:click.ctrl.exact="" //有且只有 Ctrl 被按下的时候才触发
click.exact="" //没有任何系统修饰符被按下的时候才触发
.left right middle //鼠标按钮
11. v-model 指令在表单input,textarea,select元素上创建双向数据绑定
text|textarea value作为prop,将input作为事件
checkbox|radio 使用checked属性,将change作为事件
select value作为prop,将change作为事件
<textarea v-model="message"></textarea>
单个复选框,绑定到布尔值:<input type="checkbox" v-model="blooeanVar"> //blooeanVar: true|false
多个复选框,绑定到同一个数组: new Vue({ data: {checkedNames:[]} }) //Checked names: [ "Jack", "John" ]
<input type="checkbox" value="Jack" v-model="checkedNames">
<input type="checkbox" value="qohn" v-model="checkedNames">
<input type="checkbox" value="Mike" v-model="checkedNames">
单选按钮: //new Vue({ data: {picked: ''} }) //picked: 'Two'
<input type="radio" value="One" v-model="picked">
<input type="radio" value="Two" v-model="picked">
下拉框(单): //new Vue({ data: {selected: ''} }) //selected: 'C'
<select v-model="selected"><option disabled value="">请选择</option><option>A</option><option>B</option><option>C</option></select>
下拉框(多):绑定到一个数组 //new Vue({ data:{selected: []} }) //selected: ['A', 'C']
<select v-model="selected" multiple><option>A</option><option>B</option><option>C</option></select>
用 v-for 渲染的动态选项:
<select v-model="selected">
<option v-for="option in options" v-bind:value="option.value">{{ option.text }}</option>
</select>
new Vue({
data: {
selected: 'A',
options: [
{ text: 'One', value: 'A' },
{ text: 'Two', value: 'B' },
{ text: 'Three', value: 'C' }
]
}
})
修饰符:
.lazy <input v-model.lazy="msg"> //在“change”时而非“input”时更新
.number <input v-model.number="age" type="number"> //自动将用户的输入值转为数值类型
.trim <input v-model.trim="msg"> //自动过滤用户输入的首尾空白字符
在组件上使用 v-model
有使用过vue吗?说说你对vue的理解?
说说你对SPA单页面的理解,它的优缺点分别是什么?如何实现SPA应用呢?
什么是双向绑定?原理是什么?
请描述下你对vue生命周期的理解?在created和mounted这两个生命周期中请求数据有什么区别呢?
Vue组件之间的通信方式都有哪些?
v-show和v-if有什么区别?使用场景分别是什么?
v-if和v-for的优先级是什么?如果这两个同时出现时,那应该怎么优化才能得到更好的性能?
SPA首屏加载速度慢的怎么解决?
Vue中组件和插件有什么区别?
为什么data属性是一个函数而不是一个对象?
动态给vue的data添加一个新的属性时会发生什么?怎样解决?
Vue实例挂载的过程是什么?
Vue中的$nextTick有什么作用?
说说你对vue的mixin的理解,有什么应用场景?
说说你对slot的理解?slot使用场景有哪些?
Vue.observable你有了解过吗?说说看
你知道vue中key的原理吗?说说你对它的理解
怎么缓存当前的组件?缓存后怎么更新?说说你对keep-alive的理解是什么?
Vue常用的修饰符有哪些?有什么应用场景?
你有写过自定义指令吗?自定义指令的应用场景有哪些?
Vue中的过滤器了解吗?过滤器的应用场景有哪些?
什么是虚拟DOM?如何实现一个虚拟DOM?说说你的思路
你了解vue的diff算法吗?说说看
Vue项目中有封装过axios吗?主要是封装哪方面的?
你了解axios的原理吗?有看过它的源码吗?
SSR解决了什么问题?有做过SSR吗?你是怎么做的?
使用vue开发过程你是怎么做接口管理的?
说下你的vue项目的目录结构,如果是大型项目你该怎么划分结构和划分组件呢?
vue要做权限管理该怎么做?如果控制到按钮级别的权限怎么做?
Vue项目中你是如何解决跨域的呢?
vue项目本地开发完成后部署到服务器后报404是什么原因呢?
你是怎么处理vue项目中的错误的?
Vue3有了解过吗?能说说跟Vue2的区别吗
IIFE
高阶函数
柯里化
函数式编程
偏函数
compose函数
Dart
Egg.js
微前端
前端微服务
Serverless
微格式(microformat)
BFC/IFC
WebAssembly
Taro
UniAPP
Rust语言
RESTful
渐进增强/优雅降级
polymer
Meteor
Firebase
一些数据库类型
高阶组件
Flutter
Next.js
Svelte
JAMStack
Rails
EmberJS
Mobx
Rollup