数据可视化 订阅
数据可视化,是关于数据视觉表现形式的科学技术研究。其中,这种数据的视觉表现形式被定义为,一种以某种概要形式抽提出来的信息,包括相应信息单位的各种属性和变量。 [1]  它是一个处于不断演变之中的概念,其边界在不断地扩大。主要指的是技术上较为高级的技术方法,而这些技术方法允许利用图形、图像处理、计算机视觉以及用户界面,通过表达、建模以及对立体、表面、属性以及动画的显示,对数据加以可视化解释。与立体建模之类的特殊技术方法相比,数据可视化所涵盖的技术方法要广泛得多。 展开全文
数据可视化,是关于数据视觉表现形式的科学技术研究。其中,这种数据的视觉表现形式被定义为,一种以某种概要形式抽提出来的信息,包括相应信息单位的各种属性和变量。 [1]  它是一个处于不断演变之中的概念,其边界在不断地扩大。主要指的是技术上较为高级的技术方法,而这些技术方法允许利用图形、图像处理、计算机视觉以及用户界面,通过表达、建模以及对立体、表面、属性以及动画的显示,对数据加以可视化解释。与立体建模之类的特殊技术方法相比,数据可视化所涵盖的技术方法要广泛得多。
信息
外文名
Data visualization
研究起源
二十世纪50年代
中文名
数据可视化
发展阶段
科学可视、信息可视、数据可视
数据可视化概述
数据可视化主要旨在借助于图形化手段,清晰有效地传达与沟通信息。但是,这并不就意味着数据可视化就一定因为要实现其功能用途而令人感到枯燥乏味,或者是为了看上去绚丽多彩而显得极端复杂。为了有效地传达思想概念,美学形式与功能需要齐头并进,通过直观地传达关键的方面与特征,从而实现对于相当稀疏而又复杂的数据集的深入洞察。然而,设计人员往往并不能很好地把握设计与功能之间的平衡,从而创造出华而不实的数据可视化形式,无法达到其主要目的,也就是传达与沟通信息。数据可视化与信息图形、信息可视化、科学可视化以及统计图形密切相关。当前,在研究、教学和开发领域,数据可视化乃是一个极为活跃而又关键的方面。“数据可视化”这条术语实现了成熟的科学可视化领域与较年轻的信息可视化领域的统一。
收起全文
精华内容
下载资源
问答
  • 数据可视化前言:https://blog.csdn.net/diviner_s/article/details/115933789 Apache Echarts简介:https://blog.csdn.net/diviner_s/article/details/115934089 项目最终效果图: 此篇博客为自己学习pink老师的...

    数据可视化前言:https://blog.csdn.net/diviner_s/article/details/115933789
    Apache Echarts简介:https://blog.csdn.net/diviner_s/article/details/115934089
    项目最终效果图:
    在这里插入图片描述
    此篇博客为自己学习pink老师的课后完成的项目的总结与记录,仅供交流参考。版权所有,转载请标注原作者!
    使用echarts技术做的可视图,此外其项目包含 的技术有html、css、js、jquerry、ajax、websocket、koa等。

    写到这里我们的系列文也到了前端最后一个界面,做左侧第一个柱状图跳转子界面。

    预告:下一篇开始就我们将前后端进行分离以及实现前后端交互。

    实现数据动态获取

    目的是使用同一个界面图表模板,通过点击不同的元素实现传输对应的不同数据进行展示。

    左侧跳转界面不同数据展示
    在这里插入图片描述
    右侧跳转界面不同数据展示
    在这里插入图片描述

    cookie存储信息

    Cookie 用于存储 web 页面的用户信息。在这里我们用cookie存储首页面点击柱状图元素下标
    在这里插入图片描述

    如上图,我们继续看针对左上柱状图的每个柱状体都对应着不同下标,因此我们使用cookie暂时存储下标。

    cookie创建

    • 创建cookie:document.cookie = params.dataIndex默认情况下,cookie 在浏览器关闭时删除。
      我们现在首页左上柱状图试验一下:
      这段代码位置:
      在这里插入图片描述
      我们使用如下代码,打印获取的dataIndex和cookie值:

            //4.点击柱状图跳转
            myChart1.on('click', function (params) {
              console.log('dataIndex: ' + params.dataIndex);
              document.cookie = params.dataIndex;
              console.log('cookie: ' + document.cookie);
              //cookie传递params的数组下标
              //获取统计数据
              
      		//先将跳转界面注释掉			
              //  window.location.href = 'childpage.html';
            });
      

    点击不同柱体打印的就是不同cookie值,看右侧打印情况:
    在这里插入图片描述
    因此我们已经将对应index存入cookie,接下来就是读取cookie。

    cookie读取

    在 JavaScript 中, 可以使用var x = document.cookie来读取 cookie。

    注意:document.cookie 将以字符串的方式返回所有的 cookie,类型格式: cookie1=value; cookie2=value; cookie3=value;

    返回格式是字符串+;返回,因此我们使用分隔符取“‘;”前的数。

    var jsonstr = document.cookie.split(';')[0];

    在这里插入图片描述

    子页面一

    跳转动画展示
    在这里插入图片描述
    子页面展示
    在这里插入图片描述
    子页面给出两个图表,分别是关于行业分布的柱状图和关于行业班级比例的扇形图。

    纵向柱状图

    图表还不会配置的来这里!,后面直接放代码。
    数据来源:采用Ajax的get(url,function())请求获取数据
    这里需要注意的是:function是回调函数需要获取数据后存放在ret后,在done中进行数据的解析。

    (function () {
    	// 使用cookie存点击的数据
      var jsonstr = document.cookie.split(';')[0];
    
      console.log("cookie:" + jsonstr);
      
      //ajax的get请求获取数据
      $.get("data/case0", function (ret, status) {
    
        var job = []
        var number = []
        console.log("data长度:" + ret[jsonstr].length)
        console.log(ret)
        var maxn = 0;
        for (var i = 0; i < ret[jsonstr].length; i++) {
          var name = ret[jsonstr][i].name
          var num = ret[jsonstr][i].number
          if (maxn < num) maxn = num
          console.log(name + " " + num + "  ==== ")
          job.push(name)
          number.push(num)
        }
        // console.log(job)
        // console.log(number)
    
        var mCharts1 = echarts.init(document.getElementById("div1"))
        option1 = {
          grid: { containLabel: true },
          xAxis: {
            type: 'value',
            axisLabel: {
              color: '#fff',
              fontSize: "15"
            },
            axisLine: {
              lineStyle: {
                type: 'solid',
                color: '#fff',//左边线的颜色
                //width:'1'
              }
            }
          },
          yAxis: {
            name: '职业',
            type: 'category',
            axisLabel: {
              //color: "rgba(255,255,255,.6) ",
              color: '#fff',
              fontSize: "20"
            },
            axisLine: {
              lineStyle: {
                type: 'solid',
                color: '#fff',//左边线的颜色
                //width:'1'
              }
            },
            data: job,
          },
          visualMap: { //控制颜色渐变
            orient: ' ',
            left: 'center',
            min: 1,
            max: maxn,
            textStyle: {
              fontSize: 20,
              color: '#fff'
            },
            text: ['', '就业人数:'],
            // Map the score column to color
            dimension: 0,
            inRange: {
              color: ['#65B581', '#FFCE34', '#FD665F']
            }
          },
          
          series: [{
            data: number,
            type: 'bar',
            barWidth: "50%",
            label: {
              show: false
            },
            itemStyle: {
              // 修改柱子圆角
              barBorderRadius: 10
            }
          }],
        };
    
        mCharts1.setOption(option1)
    
      });
    })();
    

    环形图

    (function () {
      var jsonstr = document.cookie.split(';')[0];
    
      //console.log("cookie2:" + jsonstr);
    
      $.get("http://127.0.0.1:8888/api/banjibili", function (ret, status) {
    
        console.log(ret)
        console.log(ret[jsonstr])
        var mCharts2 = echarts.init(document.getElementById("div2"))
        option2 = {
          tooltip: {
            trigger: 'item',
            formatter: '{b} : {c} ({d}%)'
          },
          color: [
            "#FE642E",
            "#FE9A2E",
            "#F4FA58",
            "#ACFA58",
            "#01DFD7",
            "#0096ff",
            "#8258FA",
            "#FE2E9A"
          ],
          legend: {
            top: "bottom",
            left: "center",
            //bottom: '0',
            textStyle: {
              color: '#fff',
              fontSize: 18
            }
          },
          series: [
            {
              type: 'pie',
              radius: ['40%', '70%'],
              avoidLabelOverlap: false,
              label: {
                show: false,
                position: 'center',
              },
              emphasis: {
                label: {
                  show: true,
                  fontSize: '30',
                  fontWeight: 'bold'
                }
              },
              labelLine: {
                show: false
              },
              data: ret[jsonstr]
            }
          ]
        };
        mCharts2.setOption(option2);
    
        /*******高亮显示开始**********/
        var _this2 = this
        var isSet2 = true // 为了做判断:当鼠标移动上去的时候,自动高亮就被取消
        var currentIndex2 = 0
    
        // 2、鼠标移动上去的时候的高亮动画
        mCharts2.on('mouseover', function (param) {
          isSet2 = false
          clearInterval(_this2.startCharts)
          // 取消之前高亮的图形
          mCharts2.dispatchAction({
            type: 'downplay',
            seriesIndex: 0,
            dataIndex: currentIndex2
          })
          // 高亮当前图形
          mCharts2.dispatchAction({
            type: 'highlight',
            seriesIndex: 0,
            dataIndex: param.dataIndex
          })
          // 显示 tooltip
          mCharts2.dispatchAction({
            type: 'showTip',
            seriesIndex: 0,
            dataIndex: param.dataIndex
          })
        })
        // 3、自动高亮展示
        chartHover = function () {
          var dataLen = mCharts2.getOption().series[0].data.length //计算总的数组长度
          // 取消之前高亮的图形
          mCharts2.dispatchAction({
            type: 'downplay',
            seriesIndex: 0,
            dataIndex: currentIndex2
          })
          currentIndex2 = (currentIndex2 + 1) % dataLen
          // 高亮当前图形
          mCharts2.dispatchAction({
            type: 'highlight',
            seriesIndex: 0,
            dataIndex: currentIndex2
          })
          // 显示 tooltip
          mCharts2.dispatchAction({
            type: 'showTip',
            seriesIndex: 0,
            dataIndex: currentIndex2
          })
        }
        _this2.startCharts = setInterval(chartHover, 1000)
        // 4、鼠标移出之后,恢复自动高亮
        mCharts2.on('mouseout', function (param) {
          if (!isSet2) {
            _this2.startCharts = setInterval(chartHover, 1000)
            isSet2 = true
          }
        })
        /*******高亮显示结束**********/
    
    
      });
    })();
    
    

    子页面二

    跳转动画展示
    在这里插入图片描述
    子页面展示

    在这里插入图片描述

    柱状图

    (function () {
      //不同就业去向
      var jsonstr = document.cookie.split(';')[0];
      console.log("cookie:" + jsonstr);
      $.get("http://127.0.0.1:8888/api/nannv", function (ret, status) {
    
        var data1 = ret[jsonstr].data;
        var myChart = echarts.init(document.getElementById("div1"));
        var option = {
          legend: {
            bottom: "0%",
            textStyle: {
              color: "write"
            }
          },
          tooltip: {},
          dataset: {
            dimensions: ['product', '男', '女'],
            source: data1
          },
    
          xAxis: {
            type: 'category',
            axisLabel: {
              color: '#fff',
              fontSize: "20"
            },
            axisLine: {
              lineStyle: {
                type: 'solid',
                color: '#fff',
              }
            },
          },
          yAxis: {
            name: "人数",
            axisLabel: {
              color: '#fff',
              fontSize: "20"
            },
            axisLine: {
              lineStyle: {
                type: 'solid',
                color: '#fff',
              }
            },
          },
          barWidth: "30%",
          series: [
            {
              type: 'bar', itemStyle: {
                color: new echarts.graphic.LinearGradient(0, 0, 0, 1, [{
                  offset: 0,
                  color: 'rgba(0, 221, 255)'
                }, {
                  offset: 1,
                  color: 'rgba(77, 119, 255)'
                }])
              },
              label: {
                show: true,
                position: 'top',
                color: "white",
                fontSize: 20
              },
              barGap: "20%"
            },
            {
              type: 'bar', color: new echarts.graphic.LinearGradient(0, 0, 0, 1, [{
                offset: 0,
                color: 'rgba(255, 0, 135)'
              }, {
                offset: 1,
                color: 'rgba(135, 0, 157)'
              }]),
              label: {
                show: true,
                position: 'top',
                color: "white",
                fontSize: 20
              },
            },
    
          ]
        };
        myChart.setOption(option);
      })
    })();
    

    饼图

    (function () {
      //班级男生人数
      var jsonstr = document.cookie.split(';')[0];
      $.get("http://127.0.0.1:8888/api/nannv", function (ret, status) {
        var data1 = ret[jsonstr].nan;
        //班级女生人数
        var data2 = ret[jsonstr].nv;
        var myChart = echarts.init(document.getElementById('div2'));
        var option;
        option = {
          tooltip: {
            trigger: 'item',
            formatter: function (params) {
              // do some thing
              console.log(params)
              return params.name + ":" + params.value + "人"
            }
          },
          // legend: {
          //   orient: 'vertical',
          //   left: 'left',
          //   bottom: "0%",
          //   itemWidth: 30,
          //   itemHeight: 30,
          //   textStyle: {
          //     color: "write"
          //   }
          // },
          series: [
            {
              type: 'pie',
              radius: '60%',
              itemStyle: {
                normal: {
                  label: {
                    fontSize: 20,
                    show: true,
                    position: [0, -20],
                    color: '#ddd',
                    formatter: function (params) {
                      var percent = 0;
                      var total = 0;
                      total += data1 + data2;
                      percent = ((params.value / total) * 100).toFixed(0);
                      if (params.name !== '') {
                        return params.name + ':' + percent + '%';
                      } else {
                        return '';
                      }
                    },
                  },
                  labelLine: {
                    length: 15,
                    length2: 10,
                    show: true,
                    color: '#00ffff',
                  },
                },
              },
    
              data: [
                {
                  value: data1, name: '男',
                  itemStyle: {
                    color: new echarts.graphic.LinearGradient(0, 0, 0, 1, [{
                      offset: 0,
                      color: 'rgba(0, 221, 255)'
                    }, {
                      offset: 1,
                      color: 'rgba(77, 119, 255)'
                    }])
                  }
                },
                {
                  value: data2, name: '女',
                  itemStyle: {
                    color: new echarts.graphic.LinearGradient(0, 0, 0, 1, [{
                      offset: 0,
                      color: 'rgba(255, 0, 135)'
                    }, {
                      offset: 1,
                      color: 'rgba(135, 0, 157)'
                    }])
                  }
                }
              ],
              emphasis: {
                itemStyle: {
                  shadowBlur: 10,
                  shadowOffsetX: 0,
                  shadowColor: 'rgba(0, 0, 0, 0.5)'
                }
              }
            }
          ]
        };
        myChart.setOption(option)
    
      })
    })()
    

    CSS界面布局

    两个子界面使用的同一个CSS布局

    * {
      margin: 0;
      padding: 0;
      box-sizing: border-box;
    }
    li {
      list-style: none;
    }
    /* 声明字体*/
    @font-face {
      font-family: electronicFont;
      src: url(../font/DS-DIGIT.TTF);
    }
    body {
      background: url(../images/bg.jpg) no-repeat top center;
      line-height: 1.15;
      overflow:hidden;
    }
    header {
      position: relative;
      height: 1.25rem;
      background: url(../images/head_bg.png) no-repeat;
      background-size: 100% 100%;
    }
    header h1 {
      font-size: 0.475rem;
      color: #fff;
      text-align: center;
      line-height: 1rem;
    }
    header .showTime {
      position: absolute;
      right: 0.375rem;
      top: 0;
      line-height: 0.9375rem;
      color: rgba(255, 255, 255, 0.7);
      font-size: 0.25rem;
    }
    .mainbox {
      display: flex;
      min-width: 1024px;
      max-width: 1920px;
      margin: 0 auto;
      padding: 1.4rem 0.125rem 0;
    }
    .mainbox .column {
      flex: 5;
    }
    .mainbox .column:nth-child(2) {
      flex: 3;
      margin: 0 0.125rem 0.1875rem;
      overflow: hidden;
    }
    .mainbox .panel {
      position: relative;
      height: 9rem;
      padding: 0 0.1875rem 0.1rem 0.5rem;
      border: 1px solid rgba(25, 186, 139, 0.17);
      margin-bottom: 0.1875rem;
      background: url(../images/line.png) rgba(255, 255, 255, 0.03);
    }
    .mainbox .panel::before {
      position: absolute;
      top: 0;
      left: 0;
      width: 10px;
      height: 10px;
      border-left: 2px solid #02a6b5;
      border-top: 2px solid #02a6b5;
      content: "";
    }
    .mainbox .panel::after {
      position: absolute;
      top: 0;
      right: 0;
      width: 10px;
      height: 10px;
      border-right: 2px solid #02a6b5;
      border-top: 2px solid #02a6b5;
      content: "";
    }
    .mainbox .panel .panel-footer {
      position: absolute;
      bottom: 0;
      left: 0;
      width: 100%;
    }
    .mainbox .panel .panel-footer::before {
      position: absolute;
      left: 0;
      bottom: 0;
      width: 10px;
      height: 10px;
      border-left: 2px solid #02a6b5;
      border-bottom: 2px solid #02a6b5;
      content: "";
    }
    .mainbox .panel .panel-footer::after {
      position: absolute;
      bottom: 0;
      right: 0;
      width: 10px;
      height: 10px;
      border-right: 2px solid #02a6b5;
      border-bottom: 2px solid #02a6b5;
      content: "";
    }
    .mainbox .panel h2 {
      height: 0.6rem;
      color: #fff;
      line-height: 1.6rem;
      text-align: center;
      font-size: 0.45rem;
      font-weight: 400;
    }
    
    .mainbox .panel .chart {
      height: 8rem;
    }
    
    
    


    有不懂的可以私聊我,有需要echarts.js、jQuery.js、echarts-gl.js开源库。
    评论区留下邮箱,我看到都会发给你的。


    项目源码我放在我的分享的资源里了,需要请自取

    展开全文
  • Python爬虫与数据可视化

    万次阅读 多人点赞 2019-06-12 20:57:09
    数据可视化这里特别强调,pyecharts包千万别装新版的,我这里装的是0.5.9版的其次如果要做地理坐标图,热力图啥的,必须安装地图包,比如世界地图包,中国地图包,城市地图包啥的 1.数据挖掘 代码所需包 # -*- ...

    之前写过篇爬取前程无忧职位信息并保存到Excel的博客,
    这里仔细的讲讲并且增加可视化内容

    1.数据挖掘

    代码所需包

    import urllib.request
    import xlwt
    import re
    import urllib.parse
    import time
    

    进入前程无忧官网
    我这里以搜索大数据职位信息
    在这里插入图片描述
    打开开发者模式
    Request Headers 里面是我们用浏览器访问网站的信息,有了信息后就能模拟浏览器访问
    这也是为了防止网站封禁IP,不过前程无忧一般是不会封IP的。
    在这里插入图片描述
    模拟浏览器

    header={
        'Host':'search.51job.com',
        'Upgrade-Insecure-Requests':'1',
        'User-Agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36'
    }
    

    在这里插入图片描述
    这些基本数据都可以爬取:
    为了实现交互型爬取,我写了一个能够实现输入想了解的职位就能爬取相关内容的函数

    def getfront(page,item):       #page是页数,item是输入的字符串,见后文
         result = urllib.parse.quote(item)					#先把字符串转成十六进制编码
         ur1 = result+',2,'+ str(page)+'.html'
         ur2 = 'https://search.51job.com/list/000000,000000,0000,00,9,99,'
         res = ur2+ur1															#拼接网址
         a = urllib.request.urlopen(res)
         html = a.read().decode('gbk')          # 读取源代码并转为unicode
         return html
    
    def getInformation(html):
        reg = re.compile(r'class="t1 ">.*? <a target="_blank" title="(.*?)" href="(.*?)".*? <span class="t2"><a target="_blank" title="(.*?)" href="(.*?)".*?<span class="t3">(.*?)</span>.*?<span class="t4">(.*?)</span>.*?<span class="t5">(.*?)</span>.*?',re.S)#匹配换行符
        items=re.findall(reg,html)
        return items
    

    这里我除了爬取图上信息外,还把职位超链接后的网址,以及公司超链接的网址爬取下来了。
    这里先不讲,后面后面会说到,
    接下来就需要储存信息,这里使用Excel,虽然比较麻烦,不过胜在清晰直观

    #新建表格空间
    excel1 = xlwt.Workbook()
    # 设置单元格格式
    sheet1 = excel1.add_sheet('Job', cell_overwrite_ok=True)
    sheet1.write(0, 0, '序号')
    sheet1.write(0, 1, '职位')
    sheet1.write(0, 2, '公司名称')
    sheet1.write(0, 3, '公司地点')
    sheet1.write(0, 4, '公司性质')
    sheet1.write(0, 5, '薪资')
    sheet1.write(0, 6, '学历要求')
    sheet1.write(0, 7, '工作经验')
    sheet1.write(0, 8, '公司规模')
    sheet1.write(0, 9, '公司类型')
    sheet1.write(0, 10,'公司福利')
    sheet1.write(0, 11,'发布时间')
    

    爬取代码如下,这里就能利用双层循环来实现换页爬取与换行输出
    我这里为了获得大量数据所以爬取了1000页,调试时可以只爬取几页

    number = 1
    item = input()
    for j in range(1,1000):   #页数自己随便改
        try:
            print("正在爬取第"+str(j)+"页数据...")
            html = getfront(j,item)      #调用获取网页原码
            for i in getInformation(html):
                try:
                    url1 = i[1]          #职位网址
                    res1 = urllib.request.urlopen(url1).read().decode('gbk')
                    company = re.findall(re.compile(r'<div class="com_tag">.*?<p class="at" title="(.*?)"><span class="i_flag">.*?<p class="at" title="(.*?)">.*?<p class="at" title="(.*?)">.*?',re.S),res1)
                    job_need = re.findall(re.compile(r'<p class="msg ltype".*?>.*?&nbsp;&nbsp;<span>|</span>&nbsp;&nbsp;(.*?)&nbsp;&nbsp;<span>|</span>&nbsp;&nbsp;(.*?)&nbsp;&nbsp;<span>|</span>&nbsp;&nbsp;.*?</p>',re.S),res1)
                    welfare = re.findall(re.compile(r'<span class="sp4">(.*?)</span>',re.S),res1)
                    print(i[0],i[2],i[4],i[5],company[0][0],job_need[2][0],job_need[1][0],company[0][1],company[0][2],welfare,i[6])
                    sheet1.write(number,0,number)
                    sheet1.write(number,1,i[0])
                    sheet1.write(number,2,i[2])
                    sheet1.write(number,3,i[4])
                    sheet1.write(number,4,company[0][0])
                    sheet1.write(number,5,i[5])
                    sheet1.write(number,6,job_need[1][0])
                    sheet1.write(number,7,job_need[2][0])
                    sheet1.write(number,8,company[0][1])
                    sheet1.write(number,9,company[0][2])
                    sheet1.write(number,10,("  ".join(str(i) for i in welfare)))
                    sheet1.write(number,11,i[6])
                    number+=1
                    excel1.save("51job.xls")
                    time.sleep(0.3) #休息间隔,避免爬取海量数据时被误判为攻击,IP遭到封禁
                except:
                    pass
        except:
            pass
    

    结果如下:
    在这里插入图片描述
    在这里插入图片描述

    2.数据清洗

    首先要打开文件

    #coding:utf-8
    import pandas as pd
    import re
    #除此之外还要安装xlrd包
    
    data = pd.read_excel(r'51job.xls',sheet_name='Job')
    result = pd.DataFrame(data)
    

    清洗思路:
    1、出现有空值(NAN)得信息,直接删除整行

    a = result.dropna(axis=0,how='any')
    pd.set_option('display.max_rows',None)     #输出全部行,不省略
    

    2、职位出错(很多职位都是与大数据无关的职业)
    在这里插入图片描述

    b = u'数据'
    number = 1
    li = a['职位']
    for i in range(0,len(li)):
        try:
            if b in li[i]:
                #print(number,li[i])
                number+=1
            else:
                a = a.drop(i,axis=0)
        except:
            pass
    

    3、其他地方出现的信息错位,比如在学历里出现 ‘招多少人’
    在这里插入图片描述

    b2= u'人'
    li2 = a['学历要求']
    for i in range(0,len(li2)):
        try:
            if b2 in li2[i]:
                #print(number,li2[i])
                number+=1
                a = a.drop(i,axis=0)
        except:
            pass
    

    4、转换薪资单位
    如上图就出现单位不一致的情况

    b3 =u'万/年'
    b4 =u'千/月'
    li3 = a['薪资']
    #注释部分的print都是为了调试用的
    for i in range(0,len(li3)):
        try:
            if b3 in li3[i]:
                x = re.findall(r'\d*\.?\d+',li3[i])
                #print(x)
                min_ = format(float(x[0])/12,'.2f')              #转换成浮点型并保留两位小数
                max_ = format(float(x[1])/12,'.2f')
                li3[i][1] = min_+'-'+max_+u'万/月'
            if b4 in li3[i]:
                x = re.findall(r'\d*\.?\d+',li3[i])
                #print(x)
                #input()
                min_ = format(float(x[0])/10,'.2f')
                max_ = format(float(x[1])/10,'.2f')
                li3[i][1] = str(min_+'-'+max_+'万/月')
            print(i,li3[i])
    
        except:
            pass
    

    保存到另一个Excel文件

    a.to_excel('51job2.xlsx', sheet_name='Job', index=False)
    

    这里只是简单的介绍了一些数据清理的思路,并不是说只要清理这些就行了
    有时候有的公司网页并不是前程无忧类型的,而是他们公司自己做的网页,这也很容易出错
    不过只要有了基本思路,这些都不难清理

    3.数据可视化

    数据可视化可以说是很重要的环节,如果只是爬取数据而不去可视化处理,那么可以说数据的价值根本没有发挥
    可视化处理能使数据更加直观,更有利于分析
    甚至可以说可视化是数据挖掘最重要的内容

    同样的我们先看代码需要的包

    # -*- coding: utf-8 -*-
    import pandas as pd
    import re
    from pyecharts import Funnel,Pie,Geo
    import matplotlib.pyplot as plt
    

    在这里插入图片描述

    若找不到或者安装失败,可用源码安装的方式

    在这里插入图片描述
    https://github.com/pyecharts/pyecharts

    在这里插入图片描述
    接下来就是正戏
    一样的先要打开文件

    file = pd.read_excel(r'51job2.xls',sheet_name='Job')
    f = pd.DataFrame(file)
    pd.set_option('display.max_rows',None)
    

    1、创建多个列表来单独存放【‘薪资’】【‘工作经验’】【‘学历要求’】【‘公司地点’】等信息

    add = f['公司地点']
    sly = f['薪资']
    edu = f['学历要求']
    exp = f['工作经验']
    address =[]
    salary = []
    education = []
    experience = []
    for i in range(0,len(f)):
        try:
            a = add[i].split('-')
            address.append(a[0])
            #print(address[i])
            s = re.findall(r'\d*\.?\d+',sly[i])
            s1= float(s[0])
            s2 =float(s[1])
            salary.append([s1,s2])
            #print(salary[i])
            education.append(edu[i])
            #print(education[i])
            experience.append(exp[i])
            #print(experience[i])
        except:
           pass
    

    2、matploblib库生成 工作经验—薪资图 与 学历—薪资图

    min_s=[]							#定义存放最低薪资的列表
    max_s=[]							#定义存放最高薪资的列表
    for i in range(0,len(experience)):
        min_s.append(salary[i][0])
        max_s.append(salary[i][0])
    
    my_df = pd.DataFrame({'experience':experience, 'min_salay' : min_s, 'max_salay' : max_s})				#关联工作经验与薪资
    data1 = my_df.groupby('experience').mean()['min_salay'].plot(kind='line')
    plt.show()
    my_df2 = pd.DataFrame({'education':education, 'min_salay' : min_s, 'max_salay' : max_s})				#关联学历与薪资
    data2 = my_df2.groupby('education').mean()['min_salay'].plot(kind='line')
    plt.show()
    

    在这里插入图片描述
    在这里插入图片描述
    3、学历要求圆环图

    def get_edu(list):
        education2 = {}
        for i in set(list):
            education2[i] = list.count(i)
        return education2
    dir1 = get_edu(education)
    # print(dir1)
    
    attr= dir1.keys()
    value = dir1.values()
    pie = Pie("学历要求")
    pie.add("", attr, value, center=[50, 50], is_random=False, radius=[30, 75], rosetype='radius',
            is_legend_show=False, is_label_show=True,legend_orient='vertical')
    pie.render('学历要求玫瑰图.html')
    

    在这里插入图片描述
    在这里插入图片描述
    4、大数据城市需求地理位置分布图

    def get_address(list):
        address2 = {}
        for i in set(list):
            address2[i] = list.count(i)
        address2.pop('异地招聘')
        # 有些地名可能不合法或者地图包里没有可以自行删除,之前以下名称都会报错,现在好像更新了
        #address2.pop('山东')
        #address2.pop('怒江')
        #address2.pop('池州')
        return address2
    dir2 = get_address(address)
    #print(dir2)
    
    geo = Geo("大数据人才需求分布图", title_color="#2E2E2E",
              title_text_size=24,title_top=20,title_pos="center", width=1300,height=600)
    attr2 = dir2.keys()
    value2 = dir2.values()
    geo.add("",attr2, value2, type="effectScatter", is_random=True, visual_range=[0, 1000], maptype='china',symbol_size=8, effect_scale=5, is_visualmap=True)
    geo.render('大数据城市需求分布图.html')
    

    在这里插入图片描述
    在这里插入图片描述
    5、工作经验要求漏斗图

    def get_experience(list):
        experience2 = {}
        for i in set(list):
             experience2[i] = list.count(i)
        return experience2
    dir3 = get_experience(experience)
    #print(dir3)
    
    attr3= dir3.keys()
    value3 = dir3.values()
    funnel = Funnel("工作经验漏斗图",title_pos='center')
    funnel.add("", attr3, value3,is_label_show=True,label_pos="inside", label_text_color="#fff",legend_orient='vertical',legend_pos='left')
    funnel.render('工作经验要求漏斗图.html')
    

    在这里插入图片描述
    在这里插入图片描述
    当然,pyecharts里面的图还有很多种,就靠大家去自己发掘了。

    【反馈】

    接到部分人反应的乱码情况,主要可能是因为网站规则变动。我去重新更新了一下代码,并且改进了一些地方,如果遇到爬取过程中途停下的情况,可能是网络问题或者陷入阻塞,可以重新运行一次代码

    所有代码如下:

    # -*- coding:utf-8 -*-
    import urllib.request
    import xlwt
    import re
    import urllib.parse
    import time
    header={
        'Host':'search.51job.com',
        'Upgrade-Insecure-Requests':'1',
        'User-Agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36'
    }
    def getfront(page,item):       #page是页数,item是输入的字符串
         result = urllib.parse.quote(item)					#先把字符串转成十六进制编码
         ur1 = result+',2,'+ str(page)+'.html'
         ur2 = 'https://search.51job.com/list/000000,000000,0000,00,9,99,'
         res = ur2+ur1															#拼接网址
         a = urllib.request.urlopen(res)
         html = a.read().decode('gbk')          # 读取源代码并转为unicode
         return html
    def getInformation(html):
        reg = re.compile(r'class="t1 ">.*? <a target="_blank" title="(.*?)" href="(.*?)".*? <span class="t2"><a target="_blank" title="(.*?)" href="(.*?)".*?<span class="t3">(.*?)</span>.*?<span class="t4">(.*?)</span>.*?<span class="t5">(.*?)</span>.*?',re.S)#匹配换行符
        items=re.findall(reg,html)
        return items
    #新建表格空间
    excel1 = xlwt.Workbook()
    # 设置单元格格式
    sheet1 = excel1.add_sheet('Job', cell_overwrite_ok=True)
    sheet1.write(0, 0, '序号')
    sheet1.write(0, 1, '职位')
    sheet1.write(0, 2, '公司名称')
    sheet1.write(0, 3, '公司地点')
    sheet1.write(0, 4, '公司性质')
    sheet1.write(0, 5, '薪资')
    sheet1.write(0, 6, '学历要求')
    sheet1.write(0, 7, '工作经验')
    sheet1.write(0, 8, '公司规模')
    sheet1.write(0, 9, '公司类型')
    sheet1.write(0, 10,'公司福利')
    sheet1.write(0, 11,'发布时间')
    number = 1
    item = input()
    for j in range(1,10000):   #页数自己随便改
        try:
            print("正在爬取第"+str(j)+"页数据...")
            html = getfront(j,item)      #调用获取网页原码
            for i in getInformation(html):
                try:
                    url1 = i[1]          #职位网址
                    res1 = urllib.request.urlopen(url1).read().decode('gbk')
                    company = re.findall(re.compile(r'<div class="com_tag">.*?<p class="at" title="(.*?)"><span class="i_flag">.*?<p class="at" title="(.*?)">.*?<p class="at" title="(.*?)">.*?',re.S),res1)
                    job_need = re.findall(re.compile(r'<p class="msg ltype".*?>.*?&nbsp;&nbsp;<span>|</span>&nbsp;&nbsp;(.*?)&nbsp;&nbsp;<span>|</span>&nbsp;&nbsp;(.*?)&nbsp;&nbsp;<span>|</span>&nbsp;&nbsp;.*?</p>',re.S),res1)
                    welfare = re.findall(re.compile(r'<span class="sp4">(.*?)</span>',re.S),res1)
                    print(i[0],i[2],i[4],i[5],company[0][0],job_need[2][0],job_need[1][0],company[0][1],company[0][2],welfare,i[6])
                    sheet1.write(number,0,number)
                    sheet1.write(number,1,i[0])
                    sheet1.write(number,2,i[2])
                    sheet1.write(number,3,i[4])
                    sheet1.write(number,4,company[0][0])
                    sheet1.write(number,5,i[5])
                    sheet1.write(number,6,job_need[2][0])
                    sheet1.write(number,7,job_need[1][0])
                    sheet1.write(number,8,company[0][1])
                    sheet1.write(number,9,company[0][2])
                    sheet1.write(number,10,("  ".join(str(i) for i in welfare)))
                    sheet1.write(number,11,i[6])
                    number+=1
                    excel1.save("51job.xls")
                    time.sleep(0.3) #休息间隔,避免爬取海量数据时被误判为攻击,IP遭到封禁
                except:
                    pass
        except:
            pass
    
    #coding:utf-8
    import pandas as pd
    import re
    
    data = pd.read_excel(r'51job.xls',sheet_name='Job')
    result = pd.DataFrame(data)
    
    a = result.dropna(axis=0,how='any')
    pd.set_option('display.max_rows',None)     #输出全部行,不省略
    
    b = u'数据'
    number = 1
    li = a['职位']
    for i in range(0,len(li)):
        try:
            if b in li[i]:
                #print(number,li[i])
                number+=1
            else:
                a = a.drop(i,axis=0)  #删除整行
        except:
            pass
    
    b2 = '人'
    li2 = a['学历要求']
    for i in range(0,len(li2)):
        try:
            if b2 in li2[i]:
                # print(number,li2[i])
                number += 1
                a = a.drop(i, axis=0)
        except:
            pass
    
    b3 =u'万/年'
    b4 =u'千/月'
    li3 = a['薪资']
    #注释部分的print都是为了调试用的
    for i in range(0,len(li3)):
        try:
            if b3 in li3[i]:
                x = re.findall(r'\d*\.?\d+',li3[i])
                #print(x)
                min_ = format(float(x[0])/12,'.2f')              #转换成浮点型并保留两位小数
                max_ = format(float(x[1])/12,'.2f')
                li3[i][1] = min_+'-'+max_+u'万/月'
            if b4 in li3[i]:
                x = re.findall(r'\d*\.?\d+',li3[i])
                #print(x)
                #input()
                min_ = format(float(x[0])/10,'.2f')
                max_ = format(float(x[1])/10,'.2f')
                li3[i][1] = str(min_+'-'+max_+'万/月')
            print(i,li3[i])
    
        except:
            pass
    a.to_excel('51job2.xls', sheet_name='Job', index=False)
    #############################################################################################
    import pandas as pd
    import re
    from pyecharts import Funnel,Pie,Geo
    import matplotlib.pyplot as plt
    
    file = pd.read_excel(r'51job2.xls',sheet_name='Job')
    f = pd.DataFrame(file)
    pd.set_option('display.max_rows',None)
    
    add = f['公司地点']
    sly = f['薪资']
    edu = f['学历要求']
    exp = f['工作经验']
    address =[]
    salary = []
    education = []
    experience = []
    for i in range(0,len(f)):
        try:
            a = add[i].split('-')
            address.append(a[0])
            #print(address[i])
            s = re.findall(r'\d*\.?\d+',sly[i])
            s1= float(s[0])
            s2 =float(s[1])
            salary.append([s1,s2])
            #print(salary[i])
            education.append(edu[i])
            #print(education[i])
            experience.append(exp[i])
            #print(experience[i])
        except:
           pass
    
    min_s=[]							#定义存放最低薪资的列表
    max_s=[]							#定义存放最高薪资的列表
    for i in range(0,len(experience)):
        min_s.append(salary[i][0])
        max_s.append(salary[i][0])
    #matplotlib模块如果显示不了中文字符串可以用以下代码。
    plt.rcParams['font.sans-serif'] = ['KaiTi'] # 指定默认字体
    plt.rcParams['axes.unicode_minus'] = False # 解决保存图像是负号'-'显示为方块的问题
    
    my_df = pd.DataFrame({'experience':experience, 'min_salay' : min_s, 'max_salay' : max_s})				#关联工作经验与薪资
    data1 = my_df.groupby('experience').mean()['min_salay'].plot(kind='line')
    plt.show()
    my_df2 = pd.DataFrame({'education':education, 'min_salay' : min_s, 'max_salay' : max_s})				#关联学历与薪资
    data2 = my_df2.groupby('education').mean()['min_salay'].plot(kind='line')
    plt.show()
    
    def get_edu(list):
        education2 = {}
        for i in set(list):
            education2[i] = list.count(i)
        return education2
    dir1 = get_edu(education)
    # print(dir1)
    
    attr= dir1.keys()
    value = dir1.values()
    pie = Pie("学历要求")
    pie.add("", attr, value, center=[50, 50], is_random=False, radius=[30, 75], rosetype='radius',
            is_legend_show=False, is_label_show=True,legend_orient='vertical')
    pie.render('学历要求玫瑰图.html')
    
    def get_address(list):
        address2 = {}
        for i in set(list):
            address2[i] = list.count(i)
        address2.pop('异地招聘')
        # 有些地名可能不合法或者地图包里没有可以自行删除,之前以下名称都会报错,现在好像更新了
        #address2.pop('山东')
        #address2.pop('怒江')
        #address2.pop('池州')
        return address2
    dir2 = get_address(address)
    #print(dir2)
    
    geo = Geo("大数据人才需求分布图", title_color="#2E2E2E",
              title_text_size=24,title_top=20,title_pos="center", width=1300,height=600)
    attr2 = dir2.keys()
    value2 = dir2.values()
    geo.add("",attr2, value2, type="effectScatter", is_random=True, visual_range=[0, 1000], maptype='china',symbol_size=8, effect_scale=5, is_visualmap=True)
    geo.render('大数据城市需求分布图.html')
    
    def get_experience(list):
        experience2 = {}
        for i in set(list):
             experience2[i] = list.count(i)
        return experience2
    dir3 = get_experience(experience)
    #print(dir3)
    
    attr3= dir3.keys()
    value3 = dir3.values()
    funnel = Funnel("工作经验漏斗图",title_pos='center')
    funnel.add("", attr3, value3,is_label_show=True,label_pos="inside", label_text_color="#fff",legend_orient='vertical',legend_pos='left')
    funnel.render('工作经验要求漏斗图.html')
    
    

    在这里插入图片描述
    HTML文件最好用谷歌浏览器打开,如果点开没反应可以在文件夹里找到该文件然后打开
    在这里插入图片描述

    最近比较多人说爬取数据没有动静,我去看了下,其实不是什么问题,就是网页源码有更改,之前python爬取到的信息是用HTML写的,而现在数据那里是JavaScript写的,这样的话正则肯定就不匹配了。我也花时间改了改。有些东西也去的去,加的加,不过不影响后面数据可视化。

    # -*- coding:utf-8 -*-
    import urllib.request
    import xlwt
    import re
    import urllib.parse
    import time
    header={
        'Host':'search.51job.com',
        'Upgrade-Insecure-Requests':'1',
        'User-Agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36'
    }
    def getfront(page,item):       #page是页数,item是输入的字符串
         result = urllib.parse.quote(item)					#先把字符串转成十六进制编码
         ur1 = result+',2,'+ str(page)+'.html'
         ur2 = 'https://search.51job.com/list/000000,000000,0000,00,9,99,'
         res = ur2+ur1    #拼接网址
         a = urllib.request.urlopen(res)
         html = a.read().decode('gbk')      # 读取源代码并转为unicode
         html = html.replace('\\','')       # 将用于转义的"\"替换为空
         html = html.replace('[', '')
         html = html.replace(']', '')
         #print(html)
         return html
    
    def getInformation(html):
        reg = re.compile(r'\{"type":"engine_search_result","jt":"0".*?"job_href":"(.*?)","job_name":"(.*?)".*?"company_href":"(.*?)","company_name":"(.*?)","providesalary_text":"(.*?)".*?"updatedate":"(.*?)".*?,'
                         r'"companytype_text":"(.*?)".*?"jobwelf":"(.*?)".*?"attribute_text":"(.*?)","(.*?)","(.*?)","(.*?)","companysize_text":"(.*?)","companyind_text":"(.*?)","adid":""},',re.S)#匹配换行符
        items=re.findall(reg,html)
        print(items)
        return items
    
    #新建表格空间
    excel1 = xlwt.Workbook()
    # 设置单元格格式
    sheet1 = excel1.add_sheet('Job', cell_overwrite_ok=True)
    sheet1.write(0, 0, '序号')
    sheet1.write(0, 1, '职位')
    sheet1.write(0, 2, '公司名称')
    sheet1.write(0, 3, '公司地点')
    sheet1.write(0, 4, '公司性质')
    sheet1.write(0, 5, '薪资')
    sheet1.write(0, 6, '学历要求')
    sheet1.write(0, 7, '工作经验')
    sheet1.write(0, 8, '公司规模')
    #sheet1.write(0, 9, '公司类型')
    sheet1.write(0, 9,'公司福利')
    sheet1.write(0, 10,'发布时间')
    number = 1
    item = input()
    
    for j in range(1,10):   #页数自己随便改
        try:
            print("正在爬取第"+str(j)+"页数据...")
            html = getfront(j,item)      #调用获取网页原码
            for i in getInformation(html):
                try:
                    #url1 = i[1]          #职位网址
                    #res1 = urllib.request.urlopen(url1).read().decode('gbk')
                    #company = re.findall(re.compile(r'<div class="com_tag">.*?<p class="at" title="(.*?)"><span class="i_flag">.*?<p class="at" title="(.*?)">.*?<p class="at" title="(.*?)">.*?',re.S),res1)
                    #job_need = re.findall(re.compile(r'<p class="msg ltype".*?>.*?&nbsp;&nbsp;<span>|</span>&nbsp;&nbsp;(.*?)&nbsp;&nbsp;<span>|</span>&nbsp;&nbsp;(.*?)&nbsp;&nbsp;<span>|</span>&nbsp;&nbsp;.*?</p>',re.S),res1)
                    #welfare = re.findall(re.compile(r'<span class="sp4">(.*?)</span>',re.S),res1)
                    #print(i[0],i[2],i[4],i[5],company[0][0],job_need[2][0],job_need[1][0],company[0][1],company[0][2],welfare,i[6])
                    sheet1.write(number,0,number)
                    sheet1.write(number,1,i[1])
                    sheet1.write(number,2,i[3])
                    sheet1.write(number,3,i[8])
                    sheet1.write(number,4,i[6])
                    sheet1.write(number,5,i[4])
                    sheet1.write(number,6,i[10])
                    sheet1.write(number,7,i[9])
                    sheet1.write(number,8,i[12])
                    #sheet1.write(number,9,i[7])
                    sheet1.write(number,9,i[7])
                    sheet1.write(number,10,i[5])
                    number+=1
                    excel1.save("51job.xls")
                    time.sleep(0.3) #休息间隔,避免爬取海量数据时被误判为攻击,IP遭到封禁
                except:
                    pass
        except:
            pass
    

    顺便放上源码:https://github.com/haohaizhi/51job_spiders

    因为有了自己的博客网站,后续若有修改将在新的链接中体现
    https://blog.mehoon.com/107.html

    展开全文
  • 数据可视化

    千次阅读 2019-10-22 16:01:47
    数据可视化处理可以洞察统计分析无法发现的结构和细节。例如Anscombe的四组数据(Anscombe‘s Quartet)。 狭义上:科学可视化、信息可视化、可视分析学 科学可视化 可以分为:标量场可视化、向量场可视化、张量...

    数据可视化处理可以洞察统计分析无法发现的结构和细节。例如Anscombe的四组数据Anscombe‘s Quartet)。

    狭义上:科学可视化、信息可视化、可视分析学

    科学可视化

    可以分为:标量场可视化、向量场可视化、张量场可视化

    标量场可视化:标量场指二维、三维或四维空间中每个采样处都有一个标量值的数据场。标量场的可视化一般采用映射为颜色或透明度、等值线或等值面、直接体绘制等方法。

    向量场可视化:与标量场可视化不同的是,向量场可视化以向量为单位进行采样,具有一定的方向性。

    张量场可视化:张量是矢量的延伸,标量是0阶张量,而矢量是1阶张量。张量场的可视化方法有3种,即基于纹理、几何和拓扑的可视化方法。

    信息可视化

    与科学可视化相比,信息可视化更关注抽象且应用层次的可视化问题,一般具有具体问题导向。

    根据可视化对象的不同,信息可视化可归为多个方向:

    §时空数据可视化

    §数据库及数据仓库的可视化

    §文本信息的可视化

    §多媒体或富媒体数据的可视化

    可视分析学

    是一门以可视交互为基础,综合运用图形学、数据挖掘和人机交互等技术等多个学科领域的知识,以实现人机协同完成可视化任务为主要目的分析推理性学科。

    基本模型

    顺序模型

    循环模型(与顺序模型相比,主要变化体现在:重视信息反馈、突出用户交互、强调任务导向)

    分析模型

    常用方法

    A视觉编码

    数据可视化本质是视觉编码

    1.图形元素:通常为几何图形元素,如点、线、面、体等,主要用来刻画数据的性质,决定数据所属的类型。

    2.视觉通道:图形元素的视觉属性,如位置、长度、面积、形状、方向、色调、亮度和饱和度等。

    B统计图表

    (1)饼图(Pie Chart)(2等值线(Contour Map)(3散点图(Scatter Diagram)(4维恩图(Venn Diagram)(5热地图(Heat Map6)箱线(Box-plot)图(7雷达图(Radar Chart)

    C图论方法

    社会网络中的齐美尔连带

    D视觉隐喻

    (1)直接在现实图像上进行视觉隐喻

    美国政府的机构设置

    (2)对现实事物,甚至是虚拟事物(如龙等)进行了一定的抽象处理之后,再进行视觉隐喻。比较有典型的是鱼刺图和树型结构图。

    E图形符号学

    §图形符号:点、线、面

    §位置变量:二维平面上的位置;

    §视网膜变量:尺寸、数值、纹理、颜色、方向和形状。

    F面向领域的方法

    数据可视化技术的发展呈现出了高度专业化趋势,很多应用领域已出现了自己独特的数据可视化方法,1931年,一位名叫Henry Beck的机械制图员借鉴电路图的制图方法设计出了伦敦地铁线路图。

    视觉编码

    视觉编码的关键在于找到符合目标用户群的视觉感知习惯的表达方法,同一个数据的可视化编码结果可能有多种,但对目标用户群中产生的视觉感知可能不同。

    A视觉感知

    1)视觉感知是指客观事物通过视觉感觉器官(眼睛等)在人脑中产生直接反映的过程。

    2)视觉认知是指个体对视觉感知信息的进一步加工处理过程,包括视觉信息的抽取、转换、存储、简化、合并、理解和决策等加工活动。

    完图法则(又称Gestalt法则)较好地解释了人类视觉感知和认知过程一项重要特征:人类的视觉感知活动往往倾向于将被感知对象当作一个整体去认知,并理解为与自己经验相关的、简单的、相连的、对称的或有序的以及基于直觉的完整结构。因此,视觉感知结果往往不等同于感知对象的各部分的独立感知结果之和。

    B数据类型

    从可视化处理视角看,我们可以将数据分为4个类型:定类、定序、区间型和比值型,并采用不同的视觉映射方法

    C视觉通道

    数据类型与视觉通道的对应关系图

    视觉通道的选择与展示

    在数据来源和目标用户已定的情况下,不同视觉通道的表现力不同视觉通道的表现力的评价指标包括: 

    精确性                                                          可辨认性

    可分离性                                                     视觉突出性

    由于不同视觉通道具有不同的表现力,因此数据的可视化编码过程中应忠于原始数据、目标用户的感知特征以及可视化表示的目的,选择高表现力的可视化图形元素及视觉通道。

    一般情况下采用高表现力的视觉通道表示可视化工作要重点刻画的数据或数据的特征。

    D视觉假象

    1)可视化视图所处的上下文(周边环境)可能导致视觉假象。

    2)人们对亮度和颜色的相对判断容易造成视觉假象。

    3)目标用户的经历与经验可能导致视觉假象。

    测评跳过

    应用案例

    1.美国Oakland地区犯罪数据的可视化

    Stamen Design 工作室的 Michal MigurskiTom CardenEric Rodenbeck曾研发过一种可视化应用,主要以可视化方式显示Oakland地区发生的犯罪事件的统计数据。该应用的原始数据来自CrimeWatch,并进行必要的预处理后存放在自己的数据库之中,并进一步采用数据可视化技术实现了犯罪数据的可视化显示。

    1)从实现方法选择看,主要采用了本章介绍的统计图表方法,尤其是基于地图的数据可视化方法,可以通过浏览地图的方式找到对应的统计数据。

    (2)从视觉编码角度看,其可视化图形元素及其视觉通道分别为圆圈及其填充颜色。采用不同颜色(及字母)代表了不同类型的犯罪事件,确保了较高的表现力。

    (3)从可视化结果看,提供了交互式可视化功能,较好地体现了本章介绍的反馈模型和分析模型的理念,达到了更好的用户体验。用户可以在所示的系统界面中调整可视化参数,如犯罪事件发生的起止时间、犯罪类型、具体发生的时间段等。

    (4)从可视化测评角度看,该案例较好地实现了数据可视化的几个基本原则,包括忠于原始数据、目标用户的感知特征、可视化表示的目的以及具备较强的用户体验。但是,由于数据获取困难和系统缺陷的存在,该系统对实时数据的动态可视化功能较弱。

    2.采用R语言对车辆重量与油耗之间关系数据进行可视化

     

    attach(mtcars)

    plot(wt,mpg, main="汽车重量与耗油耗间的关
          系
    ",   xlab="车重(千磅)",ylab="油耗"
          ,pch=19)

    abline(lm(mpg~wt),col="black", lwd=2, lty=1)

    lines(lowess(wt,mpg),col="blue",lwd=2,lty=2)

    install.packages("car")

    library(car)

    scatterplot(mpg ~ wt | cyl,

     data=mtcars,
     lwd=2,
     main="散点图",
     xlab="车重(千磅)",
     ylab="油耗(英里/加仑)",
     legend.plot= TRUE,
     id.method="identify",
     labels=row.names(mtcars))

     

     

     

     

     

     

     

     

    社会网络方式可视化国际贸易数据

    采用社会网络方式可视化国际贸易数据

    采用社会网络方式可视化国际贸易数

     

     

     

     

    展开全文
  • 大屏数据可视化案例

    万次阅读 多人点赞 2018-06-25 18:07:38
    数据可视化:把相对复杂的、抽象的数据通过可视的、交互的方式进行展示,从而形象直观地表达数据蕴含的信息和规律。 数据可视化是数据空间到图形空间的映射,是抽象数据的具象表达。 数据可视化交互的基本原则:总...

    数据可视化:把相对复杂的、抽象的数据通过可视的、交互的方式进行展示,从而形象直观地表达数据蕴含的信息和规律。
    数据可视化是数据空间到图形空间的映射,是抽象数据的具象表达。
    数据可视化交互的基本原则:总览为先,缩放过滤按需查看细节。

    大屏数据可视化是当前可视化领域的一项热门应用,通常可以分为信息展示类、数据分析类及监控预警类。
    大屏数据可视化应用的难点并不在于图表类型的多样化,而在于如何能在简单的一页之内让用户读懂数据之间的层次与关联,这就关系到布局、色彩、图表、动效的综合运用。如排版布局应服务于业务,避免为展示而展示;配色一般以深色调为主,注重整体背景和单个视觉元素背景的一致性。
    制作可视化大屏,最便捷有效的方式是使用DataV、帆软等报表工具,而本示例项目则使用ECharts自行开发。

    项目案例 - 上市公司全景概览
    在这里插入图片描述

    地图数据可视化 - 基于ECharts Geo
    这里写图片描述

    3D图表展示 - 基于ECharts GL
    这里写图片描述

    热力图展示 - 基于ECharts & 百度地图
    这里写图片描述

    ECharts扩展示例
    这里写图片描述

    旭日图 - 基于ECharts V4.2
    在这里插入图片描述

    地理信息数据 - ECharts & Baidu Map
    在这里插入图片描述

    项目Git地址:https://github.com/yyhsong/iDataV
    演示地址:https://yyhsong.github.io/iDataV

    后记:
    除自行开发可视化大屏外,还可以通过第三方服务来快速实现,如阿里云DataV、腾讯云图、百度Sugar等,具体可参考:https://blog.csdn.net/hwhsong/article/details/83097924

    展开全文
  • Python数据可视化
  • Python数据可视化教程:基于Plotly的动态可视化绘图

    万次阅读 多人点赞 2019-06-13 15:27:44
    Plotly是一个非常著名且强大的开源数据可视化框架,它通过构建基于浏览器显示的web形式的可交互图表来展示信息,可创建多达数十种精美的图表和地图, 下面我们以jupyter notebook为开发工具数据分析。Matplotlib存在...
  • 手把手教你做出数据可视化项目(三)3D地球旋转

    万次阅读 多人点赞 2021-05-24 21:35:14
    数据可视化前言:https://blog.csdn.net/diviner_s/article/details/115933789 项目最终效果图: 此篇博客为自己学习pink老师的课后完成的项目的总结与记录,仅供交流参考。版权所有,转载请标注原作者! 使用...
  • 【项目实战】数据爬虫 + 数据清洗 + 数据可视化

    万次阅读 多人点赞 2020-05-11 10:37:08
    自己亲手全手打了一套系统的代码,帮助朋友完成设计,做了贵阳市几个区的房屋价格爬取以及数据清洗和可视化操作,代码细细道来: 上图镇楼,接下来细说。 一:数据挖掘 我选用了链家网做数据爬取场所(不得不唠叨...
  • 数据可视化前言

    千次阅读 多人点赞 2021-04-21 09:09:16
    1. 什么是数据可视化 数据可视化就是把数据以更加直观的方式进行呈现, 我们常用图表化来对数据进行表示。 我们通过各种形式多样的图表对数据进行分许可视化,帮助人们更加直观的了解到具体信息。 2.数据可视化的...
  • 数据可视化 (1)可视化 (1)可视化的含义 定义 可视化是一种使复杂信息能够容易和快速被人理解的手段,是一种聚焦在信息重要特征的信息压缩,是可以放大人类感知的图形化表示方法。 可视化为人类大脑与...
  • 大屏数据可视化设计指南

    万次阅读 多人点赞 2019-01-03 14:25:31
    把相对复杂、抽象的数据通过可视的方式以人们更易理解的形式展示出来的一系列手段叫做数据可视化数据可视化是为了更形象地表达数据内在的信息和规律,促进数据信息的传播和应用。 在当前新技术支持下,数据可视化...
  • 数据可视化概览

    万次阅读 多人点赞 2017-12-07 12:08:07
    科学可视化(Scientific Visualization)、 信息可视化(Information Visualization)和可视分析学(Visual Analytics)三个...而将这三个分支整合在一起形成的新学科 “数据可视化”,这是可视化研究领域的新起点。
  • python数据爬取及数据可视化分析

    千次阅读 多人点赞 2021-01-06 21:54:47
    本博客是一篇集数据爬取,存储为excel表格,将数据可视化为一体的博文,数据爬取采用request等方法,数据可视化会使用图表进行展示,有改进的地方还请大家多多指教。 目录电影网站数据分析及可视化研究数据爬取环境...
  • 数据可视化概述

    千次阅读 2019-08-04 17:25:22
    数据可视化是什么 经典案例 数据可视化价值 数据可视化工具 数据可视化是什么 借助图形化手段,清晰有效传达与沟通信息 信息可视化、科学可视化、可视化分析 经典案例 数据可视化价值 ...
  • 独立的数据毫无意义,能...使用数据可视化工具进行数据可视化分析非常简单,经过简单的配置,使用者只需在B/S端简单拖拽目标数据及相关维度,即可得到从不同维度分析的结果,提升数据可视化程度,帮助决策层做出准...
  • 数据可视化数据可视化分类

    千次阅读 2015-06-01 22:03:10
    数据可视化分为:科学可视化、信息可视化,可视化分析学这三个主要分支。  科学可视化,处理科学数据,面向科学和工程领域的科学可视化,研究带有空间坐标和几何信息的三维空间测量数据、计算模拟数据和医疗影像...
  • 大屏数据可视化模板

    万次阅读 多人点赞 2019-04-30 17:20:52
    在开发大屏数据可视化项目时,除了各类报表的开发外,大屏的风格设计也是一项十分重要且耗时的工作。 本文推荐的几款大屏模板,旨在帮助那些有大屏数据可视化开发需求的同学能够快速上手,把更多的时间、精力放在...
  • 数据可视化视频精讲

    千人学习 2018-04-12 17:30:26
    本节人工智能视频涉及: (1)数据可视化的基本处理流程 (2)数据分析及其可视化的选择 (3)数据可视化结果的分析解读 (4)数据可视化的一些实际案例
  • 数据可视化都有一个共同的目的,那就是准确而高效、精简而全面地传递信息和知识。可视化能将不可见的数据现象转化为可见的图形符号,能将错综复杂、看起来没法解释和关联的数据,建立起联系和关联,发现规律和特征,...
  • 本篇文章翻译自数据可视化入门教程 数据可视化(Data Visualization)和信息可视化(Infographics)是两个相近的专业领域名词。 狭义上的数据可视化指的是数据用统计图表方式呈现,而信息可视化则是将非数字的信息...
  • ECharts实现数据可视化入门教程(超详细)

    万次阅读 多人点赞 2021-02-20 16:46:34
    ECharts实现数据可视化入门教程(超详细)ECharts介绍ECharts入门教程第一步:下载并引入scharts.js文件第二步:编写代码目录结构编写index.html代码效果展示ECharts的基础配置主要配置(常用的)案例讲解 ...
  • 结合本专栏的 「Python数据可视化AI教程」 各可视化教程配合使用。 数据介绍 1.类别数据 clothes = ["衬衫", "毛衣", "领带", "裤子", "风衣", "高跟鞋", "袜子"] drinks = ["可乐", "雪碧", "橙汁
  • 数据可视化是什么? 数据图形可视化,就是用富有色彩、图形的形式来表现数据,让人一眼望去就能概览数据,让数据更直观,让审查数据的工作更人性化。 为什么要用视觉图形来表现数据? 因为数据是无形的,而目前...
  • Python数据可视化库Seaborn

    千人学习 2019-05-20 15:45:24
    Python数据可视化库Seaborn,通过学习本教程,可以快速掌握Seaborn可视化操作。本案例中结合泰坦尼克号,鸢尾花数据,国际航班飞行数据 Python数据可视化库Seaborn,通过学习本教程,可以快速掌握Seaborn可视化操作...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 552,593
精华内容 221,037
关键字:

数据可视化