每日思考(2019/12/16)

题目概览

  • 浏览器内多个标签页之间的通信方式有哪些
  • 简述下你理解的优雅降级和渐进增强
  • 写一个判断数据类型的方法

题目解答

浏览器内多个标签页之间的通信方式有哪些

简述下你理解的优雅降级和渐进增强

  • 渐进增强(Progressive Enhancement):一开始就针对低版本浏览器进行构建页面,完成基本的功能,然后再针对高级浏览器进行效果、交互、追加功能达到更好的体验;渐进增强的写法,优先考虑老版本浏览器的可用性,最后才考虑新版本的可用性。而在现在前缀CSS3和正常CSS3都可用的情况下,正常CSS3会覆盖前缀CSS3
  • 优雅降级(Graceful Degradation):一开始就构建站点的完整功能,然后再针对低版本浏览器进行兼容。比如一开始使用 CSS3 的特性构建了一个应用,然后逐步针对各大浏览器进行 hack 使其可以在低版本浏览器上正常浏览;优雅降级的写法,优先考虑新版本浏览器的可用性,最后才考虑老版本的可用性。而在现在前缀CSS3和正常CSS3都可用的情况下,前缀CSS3会覆盖正常的CSS3
  • 如何选择:若低版本用户居多,则优先采用渐进增强的开发流程;若高版本用户居多,则为了提高大多数用户的使用体验,那当然优先采用优雅降级的开发流程;业务优先,提升用户体验永远不会排在最前面;最重要的还是保证尽可能多的用户可以正常访问网站,在此之后再考虑降级的极端情形和现代浏览器的体验增强

写一个判断数据类型的方法

  • 简易写法

    function type(obj) {
        return Object.prototype.toString.call(obj).replace(/\[object\s|\]/g, '');
    }
  • 精细封装

    /*支持
    number, boolean, string, undefined, null, symbol
    array, object, set, weakset, map, weakmap
    function, class
    regexp, date, math, promise
    */
    const _toString = Object.prototype.toString
    const NULL = 'null'
    const OBJECT = 'object'
    const NUMBER = 'number'
    const BOOLEAN = 'boolean'
    const STRING = 'string'
    const UNKNOW = 'unknow'
    
    /**
     * 
     * @param {*} element 任意类型的变量
     * @param {Boolean} strict [default: false] 是否为严格模式
     * @return {String} 变量的真实类型
     */ 
    export default function type (element, strict = false) {
      strict = !!strict
    
      // #1 fix typeof null === 'object'
      if (element === null) {
        return NULL
      }
    
      const eleType = typeof element
    
      // #2 return [number string boolean undefined symbol]
      if (eleType !== OBJECT) {
        return eleType
      }
    
      let eleRealType
      let eleRealTypeLower
    
      try {
        eleRealType = _toString.call(element).slice(8, -1)
        eleRealTypeLower = eleRealType.toLowerCase()
      } catch (e) {
        // #3 IE activie 对象
        return OBJECT
      }
    
      // #4 fix typeof new String('') === 'object' , expect 'string'
      if (eleRealTypeLower !== OBJECT) {
        // 严格模式下 会严格区分`number、string、boolean`的原始值和对象值
        // example `new String('') => 'String'`、`String('') => 'string'`
        if (strict && (eleRealTypeLower === NUMBER || eleRealTypeLower === BOOLEAN || eleRealTypeLower === STRING)) {
          return eleRealType
        }
        return eleRealTypeLower
      }
    
      if (element.constructor == Object) {
        return eleRealTypeLower
      }
    
      // #5 Object.create(null)
      try {
        // __proto__ 为部分早期浏览器
        if (Object.getPrototypeOf(element) === NULL || element.__proto__ === NULL) {
          return OBJECT
        }
      } catch (e) {
        // IE 无 Object.getPrototypeOf
      }
    
      // #6 function A () {}; new A
      try {
        const constructorName = element.constructor.name
        if (typeof constructorName === STRING) {
          return constructorName
        }
      } catch (e) {
        // No constructor
      }
    
      // function A() {}; A.prototype.constructor = null; new A
      return UNKNOW
    }

猜你喜欢

转载自www.cnblogs.com/EricZLin/p/12051977.html