在这里插入图片描述

hello,各位小伙伴,好久不见,甚是想念啊,博主开学了,最近也是乱忙一通,抽个空闲暇之余,我来教大家使用Java实现HDFS大数据分析工具,好玩又有趣,快来看看吧!
(在此之前,请大家准备好Hadoop-2.7.4-jar,电脑已安装好hadoop环境,配置虚拟机三台样机,master,slave1,slave2,其实名字用啥无所谓啦,重点在需要在三台虚拟机内部搭建好ssh免密登陆访问,可以使用普通用户身份去完成,建议不要管理员,毕竟有风险。。。Linux系统任意-最佳centos6.8以上。安装好Java服务和hadoop服务,并配置好环境变量。)
开发工具选择的依旧是教学常用的Eclipse,其实我也喜欢用IDEA,但是出教程的话,个人还是比较钟意Eclipse,好了,废话不多说,我们直接进入实践操作。
来看看实际效果图:
在这里插入图片描述
在这里插入图片描述

在这里插入图片描述

首先进入Hadoop环境搭建:为Hadoop分布式环境的搭建 准备一台虚拟机

在这里插入图片描述
*准备过程

1. 复制Linux安装文件centos6.5到D:\bigdata  (或解压缩包后再改文件夹名为centos6.5)
2. 在VMware Workstation Pro端打开D:\bigdata\centos6.5\master.vmx,添加虚拟机master
3. 虚拟机命名为master
4. 启动此虚拟机,选择我已移动此虚拟机(与原MAC地址相同),选择我已复制此虚拟机(生成新MAC地址)
5. #设置网络连接:虚拟机设置 网络适配器 自定义选择仅主机模式
   #查看MAC地址: 虚拟机设置 网络适配器 高级 复制MAC地址(备用)
   #查看IP地址:编辑 虚拟网络编辑器 查看类型为仅主机模式的子网地址192.168.109.0
   #窗口切换:ctrl+G/ctrl+alt
6. 登录
  master login: root
  password:123456

Hadoop完全分布式环境搭建
在这里插入图片描述
一、安装节点NAMENODE

1.打开master.vmx
*******命名为MASTER/master
启动虚拟机时选择:我已移动此虚拟机
00:0C:29:0B:F4:EC
2.MAC地址、IP、网络配置
(1)vi /etc/udev/rules.d/70-persistent-net.rules#ESC键 :wq!保存-->修改mac地址
(2)vi /etc/sysconfig/network-scripts/ifcfg-eth0#修改IP地址为192.168.109.125
(3)vi /etc/sysconfig/network  #修改主机名master(slave1)和网关GATEWAY=192.168.109.1
(4)service network restart   #重启网络服务
(5)vi /etc/hosts
192.168.109.125 master
192.168.109.135 slave1
192.168.109.145 slave2
(6)service network restart    #重启网络服务   ##reboot #重启主机
(7)ifconfig	 #查看网络配置

3.SSH免密登录

1)vi /etc/ssh/sshd_config
		RSAAuthentication yes # 启用 RSA 认证
		PubkeyAuthentication yes # 启用公钥私钥配对认证方式
		AuthorizedKeysFile .ssh/authorized_keys # 公钥文件路径
(2)su - user #直接切换到user根目录下
(3)mkdir .ssh		#创建目录,为了放公钥文件
(4)chmod 700 ~/.ssh	#(ssh)文件夹的权限为700,谁建谁授权
(5)ssh-keygen -t rsa -P '' #执行免密登录(config生效,生成密钥对)
(6)ll -a           #查看
(7)cd .ssh    #切换目录到.ssh下
(8)cat id_rsa.pub >> authorized_keys		#将公钥写到文件authorized_keys中
(9)chmod 600 	authorized_keys	#权限设置为60010)su root #切换到root用户下
 (11)service sshd restart #启动ssh免密登录服务
 (12)su - user  #切换到user用户下
 (13)ssh master #或者ssh 192.168.109.125 ##本机自我免密登录

二、复制节点DATANODE

(关master再复制)
名:SLAVE1
开启虚拟机是选择:我已复制此虚拟机
重新网络配置
00:0C:29:85:D1:12
(1)vi /etc/udev/rules.d/70-persistent-net.rules   #查看mac地址
(2)vi /etc/sysconfig/network-scripts/ifcfg-eth0   #修改IP地址为92.168.109.135  ##DEVICE=eth0修改为eth1 ##将MAC地址删除 HWADDR= ****
(3)vi /etc/sysconfig/network  #修改主机名master(slave1)和网关GATEWAY=192.168.109.1
(4)service network restart   #重启网络服务
(5)service sshd restart #启动ssh免密登录服务
(6)su - user  #切换到user用户下

(7)ssh slave1 #或者ssh 192.168.109.135 ##本机自我免密登录

开启虚拟机master
在master机上做免密登录slave1
  ssh slave1
在slave1机上做免密登录master
  ssh master

三、复制节点DATANODE
(关slave1再复制)
名:SLAVE2
开启虚拟机时选择:我已复制此虚拟机
00:0C:29:51:B6:74

配置过程与slave1机器配置过程相同

ssh slave2
ssh master
ssh slave2
ssh slave1
ssh slave2

四、装远程访问端

1.NEW SESSION
2.Remote host:192.168.109.125
勾选 Specify username  点 按钮(create or manage credential)
3.点 按钮 new
  Name :  USER11
  Username : user
  Password : 123456
4. 双击  Session :192.168.109.125[USER11]
5. 相同方式创建slave1和slave2的远程SESSION

安装配置JDK(使用SSH工具xshell或者Mobaxterm)

1.拖拽安装包jdk-8u121-linux-x64.tar.gz到远程端当前文件夹下(/home/user)

 2.安装JDK包
   (1)tar -zxvf jdk-8u121-linux-x64.tar.gz       #解包 jdk1.8
   (2)mv jdk1.8.0_121 jdk	 #文件夹改名,便于版本升级更换
 3.配置环境变量
   (3)vi ~/.bashrc    #编辑,修改配置环境变量,注意:行前不要有空格!
#set java environment
export JAVA_HOME=/home/user/jdk
export CLASSPATH=.:$CLASSPATH:$JAVA_HOME/lib:$JAVA_HOME/jre/lib
export PATH=$PATH:$JAVA_HOME/bin:$JAVA_HOME/jre/bin

4.配置生效

  (4)source ~/.bashrc

5.测试JDK是否安装成功

  (5)javac   # 或者 which java   

二、配置Hadoop完全分布式
1.拖拽安装包hadoop-2.6.1.tar.gz到远程端当前文件夹下(/home/user)
2.安装hadoop

  (1)tar -zxvf hadoop-2.6.1.tar.gz			#解hadoop包
  (2)mv hadoop-2.6.1 hadoop				#vi/hadoop/config#老版

3.配置完全分布式

  (3)cd hadoop/etc/hadoop/				#xml文件全部是配置文件
  (4)vi hadoop-env.sh				 	#修改JAVA_HOME
 
export JAVA_HOME=/home/user/jdk
  (5)vi core-site.xml				 	#留端口,让外部访问我
    <property>
        <name>fs.defaultFS</name>
        <value>hdfs://master:8020</value>	
    </property>
   #默认是9000,经验:hive中对接用的是8020端口,配置为9000时出错

(6)vi hdfs-site.xml

 <property>
     <name>dfs.replication</name>	#备份几份(1份)
     <value>1</value>
   </property>
   <property>
    <name>dfs.namenode.name.dir</name>   #主节点上的信息,切完之后具体信息存放在什么位置上
    <value>/home/user/hadoop/dfs/name</value>  #映射文件存放位置
  </property>
  <property>
    <name>dfs.datanode.data.dir</name>			#数据存放位置
    <value>/home/user/hadoop/dfs/data</value>
  </property>

  (7)mv mapred-site.xml.template mapred-site.xml	#改名
  (8)vi mapred-site.xml
	<property>
    <name>mapreduce.framework.name</name>
    <value>yarn</value>
  </property>

  (9)vi slaves			#所有数据节点的IP地址都写在这里#写到slaves文件/DATANODE
master				
slave1
slave2

  (10)vi yarn-site.xml 		#yarn,共享程序
  <property>
    <name>yarn.nodemanager.aux-services</name>
    <value>mapreduce_shuffle</value>
  </property>

Hadoop平台的格式化


  1.配置Hadoop环境变量  #user用户下:#专业人员用旗舰版
   (1)vi ~/.bashrc

#set hadoop environment
export HADOOP_PREFIX=/home/user/hadoop
export PATH=$HADOOP_PREFIX/bin:${PATH}
export PATH=$PATH:$HADOOP_PREFIX/sbin
   (2)source ~/.bashrc
  2.格式化Hadoop平台
   (3)hadoop namenode -format
3.复制master机的hadoop、JDK文件夹到slave1机上
scp -r ~/hadoop user@slave1:~/hadoop
scp -r ~/hadoop user@slave2:~/hadoop
scp -r ~/jdk user@slave1:~/jdk
scp -r ~/jdk user@slave2:~/jdk
scp -r ~/.bashrc user@slave1:~/.bashrc
scp -r ~/.bashrc user@slave2:~/.bashrc
slave1 和 slave2上分别 source ~/.bashrc(环境变量设置生效,JPS命令)

 4.启动Hadoop平台
   (4)start-all.sh

  5.查看进程
   (5)jps
slave1 和 slave2上分别 source ~/.bashrc(环境变量设置生效,JPS命令才好使)
*******************************************************
四、其它启动命令参考
   hadoop-daemon.sh start namenode
   hadoop-daemon.sh start datanode
   yarn-daemon.sh start resourcemanager

Windows上安装部署hadoop与Java大家可以自行百度一下,我就不多说啦!接下来直接进入HDFS大数据分析工具软件的开发:
项目结构展示:
在这里插入图片描述
效果图再放一下:
在这里插入图片描述
在这里插入图片描述
小贴士:在工具类中调用画图API的时候,这里的画图的API与原项目不在同一个类中,也不再同一个包中,怎么解决呢?可以将项目添加入依赖中,然后在类中引入依赖即可。在父类中创建成员属性,用子类去继承属性,然后就可以全局调用,注意使用关键字:volatile
在这里插入图片描述

package com.sinsy.fntp;
import org.eclipse.swt.widgets.Display;
import org.eclipse.swt.widgets.Shell;
import org.eclipse.wb.swt.SWTResourceManager;
import com.sinsy.fntp.hdfs.HDFS_API;
import com.sinsy.utils.CreateBingtu;
import org.eclipse.swt.widgets.Composite;
import java.util.Date;
import org.eclipse.swt.SWT;
import org.eclipse.swt.widgets.Menu;
import org.eclipse.swt.widgets.MenuItem;
import org.eclipse.swt.widgets.Label;
import org.eclipse.swt.widgets.Text;
import org.eclipse.swt.events.SelectionAdapter;
import org.eclipse.swt.events.SelectionEvent;
import org.eclipse.swt.graphics.Image;


public class Main extends yu{

	public Shell shlv;
	public Setting set = new Setting ();
	public HDFS_API hdfs = new HDFS_API();
	public Text lb_lcoalAddress;
	public Text lb_connect_port;
	public Text lb_current_dir;
	public Text lb_fileNumber;
	public Text log;
	public CreateBingtu image_bingtu = new CreateBingtu();
	/**
	 * Launch the application.
	 * @param args
	 */
	public static void main(String[] args) {
		try {
			Main window = new Main();
			window.open();
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

	/**
	 * Open the window.
	 */
	public void open() {
		Display display = Display.getDefault();
		createContents();
		shlv.open();
		shlv.layout();
		while (!shlv.isDisposed()) {
			if (!display.readAndDispatch()) {
				display.sleep();
			}
		}
	}

	/**
	 * Create contents of the window.
	 */
	protected void createContents() {
		Display display = Display.getDefault();
		shlv = new Shell(display,SWT.MIN);
		shlv.setImage(SWTResourceManager.getImage(Main.class, "/img/01.png"));
		shlv.setSize(451, 557);
		shlv.setText("\u946B\u8F6F\u5927\u6570\u636E\u5206\u6790V1.0.1");
		
		Composite panel_main = new Composite(shlv, SWT.BORDER);
		panel_main.setBounds(10, 0, 425, 441);
		
		Composite composite = new Composite(panel_main, SWT.BORDER);
		composite.setBounds(0, 75, 421, 362);
		
		Label lblhdfs = new Label(composite, SWT.NONE);
		lblhdfs.setBounds(153, -3, 113, 17);
		lblhdfs.setText("\u5F53\u524DHDFS\u8BE6\u7EC6\u4FE1\u606F");
		
		Label lblhdfs_1 = new Label(composite, SWT.NONE);
		lblhdfs_1.setBounds(10, 16, 113, 17);
		lblhdfs_1.setText("\u5F53\u524DHDFS\u94FE\u63A5\u5730\u5740\uFF1A");
		
		Label lblhdfs_2 = new Label(composite, SWT.NONE);
		lblhdfs_2.setBounds(10, 39, 113, 17);
		lblhdfs_2.setText("\u5F53\u524DHDFS\u8FDE\u63A5\u7AEF\u53E3\uFF1A");
		
		Label lblhdfs_3 = new Label(composite, SWT.NONE);
		lblhdfs_3.setBounds(10, 62, 113, 17);
		lblhdfs_3.setText("\u5F53\u524DHDFS\u6240\u5904\u76EE\u5F55\uFF1A");
		
		Label lblhdfs_4 = new Label(composite, SWT.NONE);
		lblhdfs_4.setBounds(10, 85, 113, 17);
		lblhdfs_4.setText("\u5F53\u524DHDFS\u6587\u4EF6\u6570\u91CF\uFF1A");
		
		Composite composite_1 = new Composite(composite, SWT.BORDER);
		composite_1.setBounds(0, 113, 417, 222);
		
		Label lblNewLabel = new Label(composite_1, SWT.NONE);
		lblNewLabel.setBounds(146, 0, 145, 17);
		lblNewLabel.setText("\u5F53\u524DHDFS\u6587\u4EF6\u6570\u636E\u5206\u6790\u56FE");
		
		Label lb_main = new Label(composite_1, SWT.NONE);
		lb_main.setImage(SWTResourceManager.getImage(Main.class, "/img/07.png"));
		lb_main.setBounds(10, 23, 393, 185);
		
		Composite composite_2 = new Composite(composite, SWT.BORDER);
		composite_2.setBounds(0, 337, 417, 21);
		
		Label lblip = new Label(composite_2, SWT.NONE);
		lblip.setFont(SWTResourceManager.getFont("Microsoft YaHei UI", 10, SWT.NORMAL));
		lblip.setBounds(10, 0, 71, 17);
		lblip.setText("\u5F53\u524D\u4E3B\u673AIP\uFF1A");
		
		Label lb_hostIP = new Label(composite_2, SWT.NONE);
		lb_hostIP.setFont(SWTResourceManager.getFont("Microsoft YaHei UI", 10, SWT.NORMAL));
		lb_hostIP.setBounds(87, 0, 126, 17);
		lb_hostIP.setText("X.X.X.X");
		
		Label lblNewLabel_6 = new Label(composite_2, SWT.NONE);
		lblNewLabel_6.setFont(SWTResourceManager.getFont("Microsoft YaHei UI", 10, SWT.NORMAL));
		lblNewLabel_6.setBounds(236, 0, 61, 17);
		lblNewLabel_6.setText("\u5F53\u524D\u65F6\u95F4\uFF1A");
		
		Label lb_date = new Label(composite_2, SWT.NONE);
		lb_date.setFont(SWTResourceManager.getFont("Microsoft YaHei UI", 10, SWT.NORMAL));
		lb_date.setBounds(303, 0, 114, 17);
		lb_date.setText("X-X-X");
		
		lb_lcoalAddress = new Text(composite, SWT.BORDER | SWT.READ_ONLY);
		lb_lcoalAddress.setFont(SWTResourceManager.getFont("Microsoft YaHei UI", 8, SWT.NORMAL));
		lb_lcoalAddress.setBounds(124, 16, 283, 17);
		
		lb_connect_port = new Text(composite, SWT.BORDER | SWT.READ_ONLY);
		lb_connect_port.setFont(SWTResourceManager.getFont("Microsoft YaHei UI", 8, SWT.NORMAL));
		lb_connect_port.setBounds(124, 39, 283, 17);
		
		lb_current_dir = new Text(composite, SWT.BORDER | SWT.READ_ONLY);
		lb_current_dir.setFont(SWTResourceManager.getFont("Microsoft YaHei UI", 8, SWT.NORMAL));
		lb_current_dir.setBounds(124, 62, 283, 17);
		
		lb_fileNumber = new Text(composite, SWT.BORDER | SWT.READ_ONLY);
		lb_fileNumber.setFont(SWTResourceManager.getFont("Microsoft YaHei UI", 8, SWT.NORMAL));
		lb_fileNumber.setBounds(124, 85, 283, 20);
		
		Label lblNewLabel_8 = new Label(panel_main, SWT.NONE);
		lblNewLabel_8.setBackground(SWTResourceManager.getColor(240, 240, 240));
		lblNewLabel_8.setBounds(0, 0, 421, 71);
		lblNewLabel_8.setImage(SWTResourceManager.getImage(Main.class, "/img/06.png"));
		
		Menu menu = new Menu(shlv, SWT.BAR);
		shlv.setMenuBar(menu);
		
		MenuItem menuItem = new MenuItem(menu, SWT.CASCADE);
		menuItem.setText("\u6587\u4EF6\u7BA1\u7406");
		
		Menu menu_2 = new Menu(menuItem);
		menuItem.setMenu(menu_2);
		
		MenuItem menuItem_4 = new MenuItem(menu_2, SWT.NONE);
		menuItem_4.addSelectionListener(new SelectionAdapter() {
			@Override
			public void widgetSelected(SelectionEvent e) {
//				一键刷新事件处理
				System.out.println("LocalHDFSAddress是:"+LocalHDFSAddress);
				 HDFS_API api = new HDFS_API();
				 api.countfile(LocalHDFSAddress,"/");
				 lb_lcoalAddress.setText(LocalHDFSAddress);
				 lb_connect_port.setText(set.SplitTheStr(LocalHDFSAddress,":","/"));
				 lb_current_dir.setText("/");
				 lb_fileNumber.setText(hdfs.countfile(LocalHDFSAddress, "/")+" 个文件");
//				 获得IP地址
				 lb_hostIP.setText(set.SplitTheStr(LocalHDFSAddress, "hdfs://", ":"));
//				 获得时间
				 lb_date.setText(df.format(new Date()));
//				 日志输出
				 log.setText("当前HDFS连接成功!");
				 log.setText(log.getText()+"\n"+"当前数据连接成功,已更新本地HDFS连接端!");
				 log.setText(log.getText()+"\n"+"正在生成数据分析图请稍后...");
//				 数据分析图
				if(imageFileOutPutPath!="") {
					 image_bingtu.Analies(imageFileOutPutPath);
					 System.out.println("图片的路径是:"+imageFileOutPutPath);
					 Image image = new Image(display,imageFileOutPutPath.replace("\\","//")+"//main.png");
					 lb_main.setImage(image);
					 log.setText(log.getText()+"\n"+"生成完成!");
				}else {
					log.setText(log.getText()+"\n"+"请先设置路径!");
				}
			}
		});
		menuItem_4.setText("\u4E00\u952E\u5237\u65B0");
		
		MenuItem menuItem_2 = new MenuItem(menu_2, SWT.NONE);
		menuItem_2.setText("\u5220\u9664\u6587\u4EF6");
		
		MenuItem menuItem_1 = new MenuItem(menu_2, SWT.NONE);
		menuItem_1.addSelectionListener(new SelectionAdapter() {
			@Override
			public void widgetSelected(SelectionEvent e) {
				new UpLoadFile().open();
			}
		});
		menuItem_1.setText("\u6587\u4EF6\u4E0A\u4F20");
		
		MenuItem menuItem_3 = new MenuItem(menu_2, SWT.NONE);
		menuItem_3.setText("\u4FEE\u6539\u6587\u4EF6");
		
		MenuItem mntmMapreduce = new MenuItem(menu_2, SWT.NONE);
		mntmMapreduce.setText("MapReduce\u5206\u6790");
		
		MenuItem btn_shezhi = new MenuItem(menu, SWT.CASCADE);
		btn_shezhi.setText("\u8BBE\u7F6E");
		
		Menu menu_1 = new Menu(btn_shezhi);
		btn_shezhi.setMenu(menu_1);
		
		MenuItem btn_menuitem_daochushezhi = new MenuItem(menu_1, SWT.NONE);
		btn_menuitem_daochushezhi.addSelectionListener(new SelectionAdapter() {
			@Override
			public void widgetSelected(SelectionEvent e) {
				new Setting().open();
			}
			
		});
		btn_menuitem_daochushezhi.setText("\u6587\u4EF6\u5BFC\u51FA\u8BBE\u7F6E");
		
		MenuItem btn_menuitem_wenjianshezhi = new MenuItem(menu_1, SWT.NONE);
		btn_menuitem_wenjianshezhi.addSelectionListener(new SelectionAdapter() {
			@Override
			public void widgetSelected(SelectionEvent e) {
				new Setting().open();
			}
		});
		btn_menuitem_wenjianshezhi.setText("\u8FDE\u63A5\u8BBE\u7F6E");
		
		MenuItem btn_about = new MenuItem(menu, SWT.NONE);
		btn_about.setText("\u5173\u4E8E");
		
		MenuItem btn_help = new MenuItem(menu, SWT.NONE);
		btn_help.setText("\u5E2E\u52A9");
		
		Composite composite_3 = new Composite(shlv, SWT.BORDER);
		composite_3.setBounds(10, 439, 425, 59);
		
		log = new Text(composite_3, SWT.BORDER | SWT.V_SCROLL | SWT.MULTI);
		log.setText("\u65E5\u5FD7\u8F93\u51FA");
		log.setBounds(0, 0, 421, 55);

	}
}

创建饼图:

package com.sinsy.utils;

import java.awt.Font;
import java.io.File;

import org.jfree.chart.ChartFactory;
import org.jfree.chart.ChartUtilities;
import org.jfree.chart.JFreeChart;
import org.jfree.chart.labels.StandardPieSectionLabelGenerator;
import org.jfree.chart.plot.PiePlot;
import org.jfree.data.general.DefaultPieDataset;

import com.sinsy.fntp.hdfs.Calculator;

public class CreateBingtu extends Calculator{
//	public static void main(String[] args) {
//		DefaultPieDataset pds = new DefaultPieDataset();
//        pds.setValue("-1℃", 27);
//        pds.setValue("0℃", 20);
//        pds.setValue("1℃", 40);
//        pds.setValue("-2℃", 71);
//        pds.setValue("-3℃", 25);
//        pds.setValue("2℃", 1);
//        String path = "C:\\Users\\Administrator\\Desktop\\2.png";
//        createPieChart(pds, path);
//	}
	public void Analies(String path) {
		DefaultPieDataset pds = new DefaultPieDataset();
		pds.setValue("*.xls文件", xlsfile/2);
		pds.setValue("*.txt", txtfile/2);
		pds.setValue("*.doc", docfile/2);
		pds.setValue("*.*", otherfile/2);
		createPieChart(pds,"HDFS本地数据分析图",path+"\\main.png",393, 185);
	}
	
	public  void createPieChart(DefaultPieDataset pds,String chartname,String filePath,int width,int height) {
        try {
            // 分别是:显示图表的标题、需要提供对应图表的DateSet对象、是否显示图例、是否生成贴士以及是否生成URL链接
            JFreeChart chart = ChartFactory.createPieChart(chartname, pds, false, false, true);
            // 如果不使用Font,中文将显示不出来
            Font font = new Font("宋体", Font.BOLD, 12);
            // 设置图片标题的字体
            chart.getTitle().setFont(font);
            // 得到图块,准备设置标签的字体
            PiePlot plot = (PiePlot) chart.getPlot();
            // 设置标签字体
            plot.setLabelFont(font);
            plot.setStartAngle(new Float(3.14f / 2f));
            // 设置plot的前景色透明度
            plot.setForegroundAlpha(0.7f);
            // 设置plot的背景色透明度
            plot.setBackgroundAlpha(0.0f);
            // 设置标签生成器(默认{0})
            // {0}:key {1}:value {2}:百分比 {3}:sum
            plot.setLabelGenerator(new StandardPieSectionLabelGenerator("{0}({1}占{2})"));
            // 将内存中的图片写到本地硬盘
            ChartUtilities.saveChartAsJPEG(new File(filePath), chart, width, height);
        } catch (Exception e) {
            e.printStackTrace();
        }  
    }

}

以上便是实现Java操作HDFS的可视化数据分析的核心代码;
更多好玩新奇的代码我将会在后续继续贴出来,以上代码仅供参考学习,未经授权请勿转载。

Logo

永洪科技,致力于打造全球领先的数据技术厂商,具备从数据应用方案咨询、BI、AIGC智能分析、数字孪生、数据资产、数据治理、数据实施的端到端大数据价值服务能力。

更多推荐