前端面试-总结-持续更新

1、js数据类型
值类型(基本类型):字符串String, 数字Number, 布尔Boolean, 对空Null, 未定义Undefined, Symbol
引用数据类型:数组Array, 对象Object,函数Function
typeof
undefined -- 未定义
string -- 字符串
number -- 数字
boolean -- 布尔
object -- 对象/null
function -- 函数

2、隐式类型转换和强制类型转换
1)、Object.prototype 定义的toString()
转为数字parseInt和parseFloat
构造函数Boolean()、Number()、String()
2)、隐式类型转换
四则运算:+ ,有一个为string,则转为string, 其他符号为number, 但是有parseInt(a) = NaN的,则为NaN
判断语句: 如if(obj),判断需要转boolean
Native代码调用:如BOM提供的alert方法接受String类型的

3、split()和join()的区别
split()是分割字符串,返回数组,带两个参数时,第二个参数指返回的数组中元素的个数
join连接多个字符/字符串,返回字符串,join()默认连接符为逗号,可以附带连接符,join("&")

4、数组方法push(), pop(), unshift(), shift()
push在数组末尾添加,返回新的数组长度
pop在数组末尾删除,返回被删除元素
unshift在数组开头添加,返回新的数组长度
shift在数组开头删除,返回被删除元素

5、IE和标准下的js区别
1)、添加事件方法
addHandler: function(element, type, handler) {
if(element.addEventListener) { //检测是否为DOM2级方法
element.addEventListener(type, handler, false);
} else if (element.attachEvent) { //检测是否为IE级方法
element.attachEvent("on" + type, handler);
} else { //检测是否为DOM0级方法
element["on" + type] = handler;
}
}
2)、移除之前添加的事件方法
removeHandler: function(element, type, handler) {
if(element.removeEventListener) {
element.removeEventListener(type, handler, false);
} else if(element.detachEvent) {
element.detachEvent("on" + type, handler);
} else {
element["on" + type] = null;
}
}
3)、获取事件及事件对象目标
//获取事件对象的兼容性写法
getEvent: function(event) {
return event ? event : window.event; //或者用arguments[0]
}
//获取事件对象目标的兼容性写法
getTarget; function(event) {
return event.target || event.srcElement;
}
4)、阻止浏览器默认事件的兼容性写法
preventDefault: function(event) {
if(event.preventDefault) {
event.preventDefault();
} else {
event.returnValue = false;
}
}
5)、阻止事件冒泡的兼容性写法
stopPropagation: function(event) {
if(event.stopPropagation) {
event.stopPropagation();
} else {
event.cancelBubble = true;
}
}

6、ajax的get和post的区别
get参数在url中,post在http请求实体中,
get请求有数据长度限制(2KB),post理论上没有
get请求数据会被浏览器缓存,post不会
安全问题,post相对来说安全一些,但是也需要做加密处理
在客户端get请求,服务器使用Request.QueryString获取参数,而post使用Request.Form

7、call、apply和bind
call(this, arg1, arg2...), 第二个参数之后为参数列表,第一个参数为null/undefined,默认指向window
apply(this, arguments), 第二个参数为数组参数
bind(this, arg1, arg2...),但是bind返回函数
低版本浏览器没有bind方法,自己实现一个
if(!Function.prototype.bind) {
Function.prototype.bind = function() {
var self = this; //保存原函数
context = [].shift.call(arguments); //保存需要绑定的this上下文
args = [].slice.call(arguments); //剩余的参数转为数组
return function() {
self.apply(context, [].concat.call(args, [].slice.call(arguments)));
}
}
})

//求最大最小值
var arr = [1, 2, 3, 89, 88]
var max = Math.max.apply(null, arr);
var min = Math.min.apply(null, arr)

//类数组转数组
var trueArr = Array.prototype.slice.apply(arrayLike)

//数组追加
var arr1 = [1, 2, 3];
var arr2 = [4, 5, 6];
var total = [].push.apply(arr1, arr2); //6
//arr1 = [1, 2, 3, 4, 5, 6]
//arr2 = [4, 5, 6]

//判断变量类型
function isArray(obj) {
return Object.prototype.toString.call(obj) = '[object Array]'
}
isArray([]) //true
isArray('ibj') //false

//call的参数使用
function fn(a, b, c) {
console.log(a, b, c);
}
var fn1 = fn.bind(null, 'Dot');
fn('A', 'B', 'C') //A, B, C
fn1('A', 'B', 'C') //Dot, A, B
fn1('B', 'C') //Dot, B, C
fn.call(null, 'Dot') //Dot, undefined, undefined
call 是把第二个及以后的参数作为 fn 方法的实参传进去,而 fn1 方法的实参实则是在 bind 中参数的基础上再往后排。

//利用call和apply做继承

8、跨域
同源策略:协议+域名+端口
同源策略限制:
1)Cookie、LocalStorage和IndexDB无法获取
2)DOM和JS对象无法获取
3)AJAX请求不能发送
跨域解决方案
1)通过jsonp跨域
2)document.domain + iframe跨域
3)location.hash + iframe
4)window.name + iframe跨域
5)postMessage跨域
6)跨域资源共享(CORS)
7)nginx代理跨域
8)nodejs中间件代理跨域
9)WebSocket协议跨域

1)通过jsonp跨域
原理引入:为了减轻web服务器的负载,把js、css、img等静态资源分离到另外一个独立域名的服务器上,
html通过相应的标签从不同域名下加载资源。基于此原理,可以通过动态创建script,请求一个带参网址实现跨域通信。
1)、原生实现:
<script>
var script = document.createElement('script');
script.type = 'text/javascript';

//传参一个回调函数给后端,方便后端返回时执行这个在前端定义的回调函数
script.src = 'http://www.domain2.com:8080/login?user=admin&callback=handleCallback';
document.head.appendChild(script);

//执行回调函数
function handleCallBack(res) {
console.log(JSON.stringfiy(res))
}
</script>
服务端返回:
handleCallBack({"status": true, "user": "admin"})

2)、jquery ajax
$.ajax({
url: 'http://www.domain2.com:8080/login',
type: 'get',
dateType: 'jsonp', //请求方式为jsonp
jsonpCallBack: 'handleCallBack', //自定义回调函数
data: {}
})

3)、vue.js
this.$http.jsonp('http://www.domain2.com:8080/login', {
params: {},
jsonp: 'handleCallBack'
}).then((res) => {
console.log(res)
})

4)、后端node.js代码
var queryString = require('querystring');
var http = require('http');
var server = http.createServer();

server.on('request', function(req, res) {
var params = qs.parse(req.url.split('?')[1]);
var fn = params.callback;

//jsonp返回设置
res.writeHead(200, {'Content-Type': 'text/javascript'});
res.write(fn + '(' + JSON.stringify(params) + ')');

res.end();
})
server.listen('8080');
console.log('Server is running at port 8080...');

jsonp的缺点:只能实现get一种请求

2) document.domain + iframe跨域
--待更新
原文地址:https://www.cnblogs.com/PearlRan/p/12073418.html