var obj = {};
obj instanceof Object; //true
var arr = [];
arr instanceof Array; //true
var now = new Date();
now instanceof Date; //true
var func = function(){};
func instanceof Function; //true
var str = "string";
str instanceof String; //false
複製代碼
var num1 = 1;
var num2 = new Number(1);
Object.prototype.toString.call(num1) == "[object Number]"; //true
Object.prototype.toString.call(num2) == "[object Number]"; //true
var arr = [];
Object.prototype.toString.call(arr) == "[object Array]"; //true
var func = function(){};
Object.prototype.toString.call(func) == "[object Function]"; //true
function A(){};
var a = new A();
Object.prototype.toString.call(a) == "[object Object]"; //true
複製代碼
console.log([].constructor == Array);
console.log({}.constructor == Object);
console.log("string".constructor == String);
console.log((123).constructor == Number);
console.log(true.constructor == Boolean);
複製代碼
let a = Symbol.for('a');
let b = Symbol.for('a');
a === b; // true
複製代碼
if(!obj){ // 控制檯會報錯obj is not defined
obj = {};
}
if(!this.obj){
alert('1')
this.obj = {};
}
if(!this.hasOwnProperty('obj')){
alert('2')
this.obj = {};
}
if(!window.obj){
alert('3')
window.obj = {};
}
複製代碼
//todo
複製代碼
typeof xx === 'object' // error null也是對象。
(xx !== null) && (typeof xx === "object") // ok
複製代碼
var x = 0;
function text() {
return this.x;
}
let o = {};
o.x = 1;
o.m = text;
// o.m.apply(); // console.log('x',x) 0 this指向全局
o.m.apply(o); // console.log('x',x) 1 this指向var,var的this仍是全局。
複製代碼
function f1() {
var n = 1;
aAdd = function () { // 沒有用var直接將值賦值給了window。
console.log('n', n); // 也能夠獲取n=1
n += 1;
}
function f2() {
return n;
}
return f2;
}
var result = f1();
aAdd();// 回調用此函數,而且加1.
result();
console.log('result', result()); // 999
console.log('aAdd', aAdd);
複製代碼
var x = {
name: 'bw2',
getName1: function() {
console.log(this) // {name: "bw2", getName1: ƒ}
},
getName2: function() {
setTimeout(() => {
console.log(this) // {name: "bw2", getName1: ƒ}
},0)
},
getName31: () => {
console.log(this) //Window
},
getName32: function() {
return function() {
console.log(this) // Window
}
}
}
x.getName1() // {name: "bw2", getName1: ƒ}
x.getName2() // {name: "bw2", getName1: ƒ}
x.getName31() // Window {stop: ƒ, open: ƒ, alert: ƒ, confirm: ƒ, prompt: ƒ, …}
x.getName32()() // Window {stop: ƒ, open: ƒ, alert: ƒ, confirm: ƒ, prompt: ƒ, …}
複製代碼
var x = {
name: 'bw2',
getName1: function() {
console.log(this)
}
}
x.getName1() // {name: "bw2", getName1: ƒ}
複製代碼
var x = {
name: 'bw2',
getName2: function() {
console.log(this) // 等同於此處的this
setTimeout(() => {
console.log(this) // 箭頭函數沒有this,繼續往上找,原始的this位置
},0)
}
}
x.getName2() // {name: 'bw2', getName1: ƒ}
複製代碼
var x = {
name: 'bw2',
getName31: () => {
console.log(this) // window
},
getName32: function() {
return function() {
console.log(this) //window
}
}
}
x.getName31() // Window {stop: ƒ, open: ƒ, alert: ƒ, confirm: ƒ, prompt: ƒ, …}
x.getName32()() // Window {stop: ƒ, open: ƒ, alert: ƒ, confirm: ƒ, prompt: ƒ, …}
複製代碼
function get(str) {
var strArray = str.split('-');
for(let i = 0 ;i < strArray.length; i++){
if(i > 0){
strArray[i] = strArray[i].slice(0, 1).toUpperCase() + strArray[i].slice(1)
}else {
strArray[i] = strArray[i];
}
}
return strArray.join('');
}
let b = get('get-element-by-id');
複製代碼
1.不要在同一行聲明多個變量。
2.請使用 ===/!==來比較true/false或者數值
3.使用對象字面量替代new Array這種形式
4.不要使用全局函數。
5.Switch語句必須帶有default分支
6.函數不該該有時候有返回值,有時候沒有返回值。
7.For循環必須使用大括號
8.If語句必須使用大括號
9.for-in循環中的變量 應該使用var關鍵字明確限定做用域,從而避免做用域污染。
複製代碼
//淺拷貝一、ES6:object.assign()
var a = { name : 「hello」 };
var b = Object.assign( { },a );
b.name = 「hi」;
console.log(a);
複製代碼
// 淺拷貝二、展開運算符……
擴展運算符用三個點號表示,功能是把數組或類數組對象展開成一系列用逗號隔開的值
var a = { name : 「hello」 };
var b = { …a};
b.name = 「hi」;
console.log(a);
複製代碼
//淺拷貝三、本身封裝函數實現for in
var a = { name : 「hello」 };
var b = copy(a);
b.name = ‘hi’;
console.log(a);
function copy(obj){
var result = { };
for(var attr in obj ){
result [attr] = obj[attr];
}
return result;
}
複製代碼
```
//深拷貝1
var dest = JSON.parse(JSON.stringify(target));
//深拷貝2
var deepCopy= function(source) {
var result={};
for (var key in source) {
result[key] = typeof source[key]===’object’? deepCoyp(source[key]): source[key];
}
return result;
}
// 深拷貝3 reduce
function deepClone(a) {
const keys = Object.keys(a)
return keys.reduce((memo, current) => {
const value = a[current]
if (typeof value === 'object') {
return {
...memo,
[current]: deepClone(value),
}
}
return {
...memo,
[current]: value,
}
}, {})
}
var a = {
val: 1,
desc: {text: 'a'},
}
var b = deepClone(a)
//深拷貝4 第三方類庫
Lodash merge函數
immutable
```
複製代碼
var obj = {
message: 'My name is: '
}
function getName(firstName, lastName) {
console.log(this.message + firstName + ' ' + lastName)
}
getName.call(obj, 'Dot', 'Dolby')
複製代碼
var obj = {
message: 'My name is: '
}
function getName(firstName, lastName) {
console.log(this.message + firstName + ' ' + lastName)
}
getName.apply(obj, ['Dot', 'Dolby'])// My name is: Dot Dolby
複製代碼
var obj = {
name: 'Dot'
}
function printName() {
console.log(this.name)
}
var dot = printName.bind(obj)
console.log(dot) // function () { … }
dot() // Dot
複製代碼
//一樣bind也能夠有多個參數,而且參數能夠執行的時候再次添加,可是要注意的是,參數是按照形參的順序進行的。
var a = {
user:"追夢子",
fn:function(e,d,f){
console.log(this.user); //追夢子
console.log(e,d,f); //10 1 2
}
}
var b = a.fn;
var c = b.bind(a,10);
c(1,2);
複製代碼
Adobe Flash Socket 、
ActiveX HTMLFile (IE) 、
基於 multipart 編碼發送 XHR 、
基於長輪詢的 XHR
複製代碼
// websocket怎麼用?
複製代碼
var globalVar = 'global var';
function test() {
alert(globalVar); // undefined, 由於globalVar在本函數內被重定義了,致使全局失效,這裏使用函數內的變量值,但是此時還沒定義
var globalVar = 'overrided var'; // globalVar在本函數內被重定義
alert(globalVar); // overrided var
}
alert(globalVar); // global var,使用全局變量
複製代碼
dd?
複製代碼
window.onerror = function(message, url, line) {
if (!url) return;
var msg = {};
//記錄客戶端環境
msg.ua = window.navigator.userAgent;
//只記錄message裏的message屬性就行了,
//錯誤信息可能會比較晦澀,有些信息徹底無用,應酌情過濾
msg.message = message.message;
msg.url = url;
msg.line = line;
msg.page = window.location.href;
var s = [];
//將錯誤信息轉換成字符串
for(var key in msg){
s.push(key + '=' + msg[key]);
}
s = s.join('&');
//這裏是用增長標籤的方法調用日誌收集接口,優勢是比較簡潔。
new Image().src = '/ajax-jserror.php?' + encodeURIComponent(s) + '&t=' + Math.random();
};
複製代碼
(() => {
var a = b = 3;
})()
console.log(a) // a is not defined
console.log(b) // 3
// 等價於 b=3 && var a=b
// 因此console時,a不存在,b爲3
複製代碼
function debounce(func, delay) {
let timeOut = null; // 定義一個定時器函數;
return function () {
if(timeOut !== null){ // 若是已經賦值了,就清空定時器從新計算。
clearTimeout(timeOut);
}
timeOut = setTimeout(func,delay); //每次觸發就賦值,執行最後一次賦值的函數
}
}
function handle() {
console.log('抖動')
}
window.addEventListener('scroll',debounce(handle,500))
複製代碼
// 應用場景:頁面resize 頁面scroll, input輸入效驗,搜索
var throttle = function (func, delay) {
let time = null;
return function () {
let _this = this;
if(!time) { // 若是已經賦值就不要執行(賦值)了,
time = setTimeout(function () { // 經過賦值
func.apply(_this, arguments); // func 參數
time = null; // 約定時間執行完後 賦值爲null 新的生命週期開始
}, delay)
}
}
};
function doSomfun(){
console.log('節流',Math.random());
};
window.addEventListener('scroll',throttle(doSomfun, 1000))
複製代碼
function commafy(num) {
return num && num
.toString()
.replace(/(\d)(?=(\d{3})+\.)/g, function($0, $1) {
return $1 + ",";
});
}
console.log(commafy(1234567.90)); //1,234,567.90
複製代碼
let a = {};
let b = 1;
a.valueOf = function () {
console.log(b);
return b++;
}
console.log(a == 1 && a == 2 && a == 3);
複製代碼
let b = 1;
Object.defineProperty(window, 'a', {
get() {
console.log(b)
return b++;
}
})
console.log(a === 1 && a === 2 && a === 3);
複製代碼
document.querySelectorAll("input[type='radio']").forEach(item => console.log(item.checked)); // 能夠拿取選中的那個。
複製代碼
/**
* 從零字符串中讀取文件名.
* @param {String}filePath
* @return {String}
* @example
* getFileName('/user/document/abc.doc') //=> abc.doc;
*/
function getFileName(filePath) {
// 最笨實現
// 可繼續追問的點:
// 1. 是否能夠省去這個臨時數組?
let pathList = filePath.split('/')[0];
return pathList[ pathList.length - 1] || '';
// 正則實現
// 可繼續追問的點:
// 1. 用正則如何判斷最後一級路徑?
let match = /\/([^/]*)$/.match(filePath);
return match && match[1] ? match[1] : '';
// 最佳實現
let posi = filePath.lastIndexOf('/');
return posi > -1 ? filePath.slice(posi + 1) : '';
}
複製代碼
/* --------- 找出最接近的值 ----------- */
/* 儘可能不使用 JS 特有的語法糖,儘可能不使用如 Array.sort 等語言特有的方法。*/
const arr2 = [1, 5, 9, 15, 28, 33, 55, 78, 99];
/**
* 返回最接近輸入值的數字,若是有多個,返回最大的那個
* @param {number} n
* @return {number}
*/
function findMoreThanHalf(arr) {
// todo
}
// 測試用例
console.log(findMoreThanHalf([0])) // 0
console.log(findMoreThanHalf([0,1])) // -1
console.log(findMoreThanHalf([0,1,2,2])) // -1
console.log(findMoreThanHalf([0,1,2,2,2])) // 2
console.log(findMoreThanHalf([0,1,2,3,3,3])) // -1
console.log(findMoreThanHalf([0,1,2,3,3,3,3])) // 3
複製代碼
/* --------- 數組洗牌 ----------- */
/* 儘可能不使用 JS 特有的語法糖,儘可能不使用如 Array.sort 等語言特有的方法。*/
const arr = [3, 1, 22, 13, 5, 37, 42, 15, 5, 79, 38, 8, 28, 9];
/**
* 不建立新的數組,返回原有數組,打亂裏面的數字順序,考慮性能,時間複雜度越低越好
* @param {number[]} arr
* @return {number[]}
*/
function shuffle(arr) {
// todo
}
複製代碼
const url = 'http://sample.com/?a=1&b=2&c=xx&d#hash';
/**
* 返回 URL 參數中的 QueryString
* @param url {string}
* @return {Object}
* @example
* parseQueryString('http://sample.com/?a=1&b=2&c=xx&d&&==#hash')
* -> { a: '1', b: '2', c: 'xx', d: '' };
*/
function parseQueryString(url) {
// todo
}
複製代碼
/**
* 從頁面根節點開始,遍歷頁面上全部 DOM 元素,而且返回每一個DOM標籤的名稱和出現次數
* 分別用「深度優先」和「廣度優先」的策略來實現
* @param {HTMLElement} 頁面根節點
* @return {Object} - 包含頁面上全部標籤名-該標籤出現次數的對象,eg: { div: 10, p: 20, h1: 3 }
*/
function collectAllElements(e) {
// your code here...
}
複製代碼
// 入參格式參考:
const arr = [
{ id: 1, name: 'i1' },
{ id: 2, name: 'i2', parentId: 1 },
{ id: 4, name: 'i4', parentId: 3 },
{ id: 3, name: 'i3', parentId: 2 },
{ id: 8, name: 'i8', parentId: 7 }
];
/* 能夠將數組轉化爲樹狀數據結構,要求程序具備偵測錯誤輸入的能力*/
function buildTree(arr) {
/**
* 此處寫代碼邏輯
*/
}
複製代碼
/**
分別用「深度優先」和「廣度優先」的策略來實現
@param {HTMLElement} - e
@return {HTMLElement[]}
*/
function collectAllElements(e) {
// your code here...
}
複製代碼
var data = [
{ userId: 8, title: 'title1'},
{ userId: 11, title: 'other'},
{ userId: 15, title: null},
{ userId: 19, title: 'title2'}
];
var find = function(origin) {
// your code here...
}
//查找data中,符合條件的數據,並進行排序
var result = find(data).where({
"title": /\d$/
}).orderBy('userId', 'desc');
console.log(result); // [{ userId: 19, title: 'title2'}, { userId: 8, title: 'title1' }];
複製代碼
var tpl = template('<p>hey there {{ name }}</p>');
var div = document.createElement('div');
div.innerHTML = tpl({ name: 'Neo' });
document.body.appendChild(div);
複製代碼
const htmlStr = `
<div class="widget-body" data-spm-anchor-id="a1z4o.xxss.i3.14803e15bAFF41">
<span class="ctr-val g-csscut-more" style="display: inline-block;vertical-align: top;width:200px;」><a target="_blank" href="positionDetail.htm?id=44106" title="歡迎應聘螞蟻金服支付寶前端工程師-杭州、上海、北京、成都">歡迎應聘螞蟻金服支付寶前端工程師-杭州、上海、北京、成都</a></span> </div>` function astParser(){ // todo } 複製代碼
<div id="container" style="border:1px solid red; position: absolute; width:100px; height: 100px">something</div>
<script>
//todo
</script>
複製代碼
// 2. 具有 off 方法解綁事件
function EventEmitter () {
// TODO
}
var emitter = EventEmitter();
emitter.on('foo', function(e){
console.log('listening foo event 1', e);
});
emitter.on('foo', function(e){
console.log('listening foo event 2', e);
});
emitter.on('bar', function(e){
console.log('listening bar event', e);
});
// 監聽所有事件
emitter.on('*', function(e){
console.log('listening all events');
});
emitter.trigger('foo', {name : 'John'});
emitter.trigger('bar', {name : 'Sun'});
emitter.trigger('*', {name : 'Sun'});
emitter.off('foo');
複製代碼
var Class = {};
Class.create = function(props){
// TODO
};
var Animal = Class.create({
sleep : function(){
console.log("zzzzzz~");
}
});
var Person = Animal.extend({
constructor : function(){
this.type = "Person";
},
speak : function(){
console.log("hello world!");
}
});
var qitao = new Person("Qitao");
qitao instanceof Person
qitao instanceof Animal
複製代碼
var x = 1;
function ScopeTest(){
alert( x ); // undefined
var x = 'hello world';
alert( x ); //hello world
}
ScopeTest();
複製代碼
// JS在執行每一段JS代碼以前, 都會首先處理var關鍵字和function定義式(函數定義式和函數表達式)
function test(xxx){
alert(xxx); // function
var xxx = 123;
function xxx(){}
alert(xxx); //123
}
test(444); //先彈出function而後123.
複製代碼
console.log(1);
setTimeout(function() {
console.log(2);
}, 0);
console.log(3);
// 132
複製代碼
var x = 1;
function ScopeTest(){
alert( x ); // 1
}
複製代碼
var name = 'laruence';
function echo()
{
alert(name);
}
function env()
{
var name = 'eve';
echo();
}
env(); // laruence
複製代碼
若是你想要實現支持setter和getter特性的拷貝,該怎麼實現?javascript
若是遍歷一個Object對象? for…in…, for…of… 的區別是什麼? forEach、map、filter、some、every函數的區別?php
body中添加li標籤css
在一個body中插入十個<ul><li>第i項</li></ul>,考慮效率和性能
var str='<ul>'',$body; for(var i = 1;i<=10;i++){ str+='<li>第'+i+'項</li>' } str+='</ul>' $body=typeof document.querySelectorAll=='function'?document.querySelectorAll('body')[0]:document.getElementsByTagName('body')[0]; $body.innerHtml+=str; 複製代碼
var t=4;
function foo(){
var tem=12;
funciton bar(){
var temo=34;
console.log(t+" "+tem+" "+temo);
}
}
複製代碼