• d3基础入门一-选集、数据绑定等核心概念


     引入D3

    D3下载,本文下载时的版本为6.5.0

    mkdir d3.6.5.0                                          
    unzip --help                                            
    unzip d3.zip -d d3.6.5.0/                               
    ls d3.6.5.0/                                            
    API.md  CHANGES.md  d3.js  d3.min.js  LICENSE  README.md
    $ ls
    01_empty.html  static
    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>import d3</title>
        <script type="text/javascript" src="static/d3.6.5.0/d3.js"></script>
    </head>
    <body>
    <script type="text/javascript">
        alert(1);
    </script>
    </body>
    </html>

    python3

    python -m http.server 8801 &

    python2

    python -m SimpleHTTPServer 8801 &

    http://127.0.0.1:8801/01_empty.html

    D3的选集

    JS控制台中输入

    d3.select("body")

     返回的是一个JS对象,除了原型prototype外,主要有两个数组,

    _groups 自己相关及其子元素相关信息

    _parents 父元素相关,body的父元素就是html了

    这个空页面,所以body中没有元素,下面添加多个元素,

    <p>11</p>
    <p>12</p>
    <p>13</p>

    在JS控制台上输入 

    selectAll与select的不同是,_groups数组中的每个元素都是一个NodeList

     

     D3数据绑定

    <body>
    <p>11</p>
    <p>12</p>
    <p>13</p>
    
    <script type="text/javascript">
        let dataset = [1,2,3,4,5]
        d3.selectAll("p")
            .data(dataset);
    </script>
    </body>

    data() 将五个数据绑定到三个元素

     可以看到元素还是三个,但每个元素上多了一个__data__属性,它的值对应的是数组中的元素

    <script type="text/javascript">
        let dataset = [1,2,3,4,5]
        d3.selectAll("p")
            .data(dataset)
            .enter();
    </script>

     创建一个选集,就是初始化两个数组

    function Selection(groups, parents) {
      this._groups = groups;
      this._parents = parents;
    }

    然后使用原型构建一系列方法,开头这6个方法非常重要,弄清理它们的作用有助于深入了解D3

    Selection.prototype = selection.prototype = {
      constructor: Selection,
      select: selection_select,
      selectAll: selection_selectAll,
      filter: selection_filter,
      data: selection_data,
      enter: selection_enter,
      exit: selection_exit,

    enter()方法是创建一个新的选集并返回这个选集,重点就是其传入的参数:this._enter,

    var sparse = function(update) {
      return new Array(update.length);
    };
    
    var selection_enter = function() {
      return new Selection(this._enter || this._groups.map(sparse), this._parents);
    };

    this._enter这个属性是在data()方法中完成初始化的,data()这个方法稍微复杂,请直接看最后四行

    var selection_data = function(value, key) {
      if (!value) {
        data = new Array(this.size()), j = -1;
        this.each(function(d) { data[++j] = d; });
        return data;
      }
    
      var bind = key ? bindKey : bindIndex,
          parents = this._parents,
          groups = this._groups;
    
      if (typeof value !== "function") value = constant$1(value);
    
      for (var m = groups.length, update = new Array(m), enter = new Array(m), exit = new Array(m), j = 0; j < m; ++j) {
        var parent = parents[j],
            group = groups[j],
            groupLength = group.length,
            data = value.call(parent, parent && parent.__data__, j, parents),
            dataLength = data.length,
            enterGroup = enter[j] = new Array(dataLength),
            updateGroup = update[j] = new Array(dataLength),
            exitGroup = exit[j] = new Array(groupLength);
    
        bind(parent, group, enterGroup, updateGroup, exitGroup, data, key);
    
        // Now connect the enter nodes to their following update node, such that
        // appendChild can insert the materialized enter node before this node,
        // rather than at the end of the parent node.
        for (var i0 = 0, i1 = 0, previous, next; i0 < dataLength; ++i0) {
          if (previous = enterGroup[i0]) {
            if (i0 >= i1) i1 = i0 + 1;
            while (!(next = updateGroup[i1]) && ++i1 < dataLength);
            previous._next = next || null;
          }
        }
      }
    
      update = new Selection(update, parents);
      update._enter = enter;
      update._exit = exit;
      return update;
    };

     在data()方法中完成了两个重要属性的初始化_enter,_exit,并返回一个新的选集

    enter()

    <script type="text/javascript">
        var dataset = [1,2,3,4,5]
        var enter = d3.selectAll("p")
            .data(dataset)
            .enter();
        var jsonStr = JSON.stringify(enter);
        alert(jsonStr);
    
    </script>

    从输出上可以看到enter是一个选集,它比一个空的选集包含的内容更少

    {"_groups":
    [[null,null,null,
    {"ownerDocument":{
    "location":{
    "href":"file:///opt/wks/d3/d3-book-master/d3_demo/03_dataset.html",
    "origin":"null",
    "protocol":"file:","host":"","hostname":"","port":"",
    "pathname":"/opt/wks/d3/d3-book-master/d3_demo/03_dataset.html","search":"","hash":""}},
    "namespaceURI":"http://www.w3.org/1999/xhtml","_next":null,"_parent":{},
    "__data__":4},
    {"ownerDocument":{"location":{"href":"file:///opt/wks/d3/d3-book-master/d3_demo/03_dataset.html","origin":"null","protocol":"file:","host":"","hostname":"","port":"","pathname":"/opt/wks/d3/d3-book-master/d3_demo/03_dataset.html","search":"","hash":""}},"namespaceURI":"http://www.w3.org/1999/xhtml","_next":null,"_parent":{},

    "__data__":5}]],

    "_parents":[{}]}

    enter选集_groups 总共有5个元素,前三为空,后两个为绑定的数据元素的对象

    前面说将五个数据绑定到三个存在的元素上,后面两个数据元素,D3为其绑定一个“待初始化的对象”上。

    enter选集 = 数据集合 - DOM集合 ,代表数据集合中没有绑定DOM的、未可视化的选集对象。

    现在我们将集合分为三类:

    enter() :  数据集合中没有绑定DOM的、未可视化的选集对象。

    data()   : 数据集合中绑定DOM的、可视化的选集对象。

    exit()    : DOM集合中没有关联数据的选集对象,或者是数据退出的DOM对象选集。

    其他选集:

    merge() : enter() 是未可视化的数据选集,那么初始化完enter()的选集后,想要一个全集时,就可以使用merge(),得到一个新旧合并的D3选集。

     merge(bars)  merge的参数是一个绑定的数据的选集,merge会返回当时最新的图形和数据绑定的选集。

     //Select…
    var bars = svg.selectAll("rect")
       .data(dataset, keyFunc);        //Bind data with custom key function

    如何确定数据

    data(dataset)          按数组dataset的索引确定数组,通常数组的中元素是简单类型

    data(dataset,key)   按指定的方法key确定数组中的元素,通常数组中的元素是JS对象

  • 相关阅读:
    ES9新内容概括
    TensorFlow --- 01初识
    机器学习算法 --- SVM (Support Vector Machine)
    机器学习算法 --- Naive Bayes classifier
    机器学习算法 --- Pruning (decision trees) & Random Forest Algorithm
    机器学习算法 --- Decision Trees Algorithms
    机器学习算法 --- 逻辑回归及梯度下降
    机器学习算法 --- 线性回归
    机器学习基础 --- pandas的基本使用
    机器学习基础 --- numpy的基本使用
  • 原文地址:https://www.cnblogs.com/perfei/p/14456431.html
Copyright © 2020-2023  润新知