import { isSymbol } from './lang' ; import { generateUUID } from './uuid' ; export function isObject ( value ) { return value !== null && typeof value === 'object' ; } export function isPromise ( value ) { return value && typeof value . then === 'function' ; } export function isPlainObject ( value ) { if ( value === null || typeof value !== 'object' ) return false ; const proto = Object . getPrototypeOf ( value ) ; return proto === Object . prototype || proto === null ; } /**
 * 对数组从小到大排序
 */ export function sortBy < T > ( arr , func ? ) { const length = arr . length ; for ( let i = 0 ; i < length ; i ++ ) { for ( let j = i + 1 ; j < length ; j ++ ) { const itemI = arr [ i ] ; const itemJ = arr [ j ] ; const indicatorI = func ? func ( itemI ) : itemI ; const indicatorJ = func ? func ( itemJ ) : itemJ ; if ( indicatorJ < indicatorI ) { arr [ i ] = itemJ ; arr [ j ] = itemI ; } } } return arr ; } export function includes < T > ( array , item ) { return array . indexOf ( item ) > - 1 ; } export function remove < T > ( array , item ) { const index = array . indexOf ( item ) ; if ( index > - 1 ) { array . splice ( index , 1 ) ; } } export function batchRemove < T > ( array , items ) { items . forEach ( ( item ) => { const index = array . indexOf ( item ) ; if ( index > - 1 ) { array . splice ( index , 1 ) ; } } ) ; } export function batchRemoveFromSet < T > ( set , items ) { items . forEach ( ( item ) => { set . delete ( item ) ; } ) ; } export function isPrimitive ( value ) { return value === null || ( typeof value !== 'object' && typeof value !== 'function' ) ; } export function convert2UniqueString ( key ) { if ( ! isSymbol ( key ) ) { return ( key as string | number ) . toString ( ) ; } return ( key as symbol ) . toString ( ) + generateUUID ( ) ; } export const deduplicate = < T > ( array ) : T [ ] => Array . from ( new Set ( array ) ) ; const promise = Promise . resolve ( ) ; /**
 * nextTick would flush promise micro task
 */ export function nextTick ( fn ? ) { return fn ? promise . then ( fn ) : promise ; } export const hasOwn = ( val , key ) : key is keyof typeof val => Object . prototype . hasOwnProperty . call ( val , key ) ; export function is ( x , y ) { if ( x === y ) { return x !== 0 || 1 / x === 1 / y ; } return x !== x && y !== y ; } export function bind ( fn , ctx ) { function boundFn ( a ? ) { const l = arguments . length ; return l ? l > 1 ? fn . apply ( ctx , arguments ) : fn . call ( ctx , a ) : fn . call ( ctx ) ; } return boundFn ; } export function shallowEqual ( objA , objB ) { if ( is ( objA , objB ) ) return true ; if ( typeof objA !== 'object' || objA === null || typeof objB !== 'object' || objB === null ) { return false ; } const keysA = Object . keys ( objA ) ; const keysB = Object . keys ( objB ) ; if ( keysA . length !== keysB . length ) return false ; for ( let i = 0 ; i < keysA . length ; i ++ ) { if ( ! objB . hasOwnProperty ( keysA [ i ] ) || ! is ( objA [ keysA [ i ] ] , objB [ keysA [ i ] ] ) ) { return false ; } } return true ; } export const dummy = ( ) => { } ; export function loadJSON ( url ) { return new Promise ( ( resolve ) => { const xhr = new XMLHttpRequest ( ) ; xhr . overrideMimeType ( 'application/json' ) ; xhr . open ( 'GET' , url , true ) ; xhr . onreadystatechange = function ( ) { if ( xhr . readyState === 4 && xhr . status === 200 ) { resolve ( JSON . parse ( xhr . responseText ) ) ; } } ; xhr . send ( null ) ; } ) ; }