Apache Spark 什么时候开始支持集成 Hive 功能?笔者相信只要使用过 Spark 的读者,应该都会说这是很久以前的事情了。

那 Apache Flink 什么时候支持与 Hive 的集成呢?读者可能有些疑惑,还没有支持吧,没用过?或者说最近版本才支持,但是功能还比较弱。

其实比较也没啥意义,不同社区发展的目标总是会有差异,而且 Flink 在真正的实时流计算方面投入的精力很多。不过笔者想表达的是,Apache Hive 已经成为数据仓库生态系统的焦点,它不仅是一个用于大数据分析和 ETL 的 SQL 引擎,也是一个数据管理平台,所以无论是 Spark,还是 Flink,或是 Impala、Presto 等,都会积极地支持集成 Hive 的功能。

的确,对真正需要使用 Flink 访问 Hive 进行数据读写的读者会发现,Apache Flink 1.9.0 版本才开始提供与 Hive 集成的功能。不过,值得欣慰的是,Flink 社区在集成 Hive 功能方面付出很多,目前进展也比较顺利,最近 Flink 1.10.0 RC1 版本已经发布,感兴趣的读者可以进行调研和验证功能。

架构设计

首先,笔者基于社区公开的资料以及博客,概括性地讲解 Flink 集成 Hive 的架构设计。

Apache Flink 与 Hive 集成的目的,主要包含了元数据和实际表数据的访问。

元数据

为了访问外部系统的元数据,Flink 刚开始提供了 ExternalCatalog 的概念。但是 ExternalCatalog 的定义非常不完整,基本处于不可用的状态。Flink 1.10 版本正式删除了 ExternalCatalog API (FLINK-13697),这包括:

  • ExternalCatalog(以及所有依赖的类,比如 ExternalTable)
  • SchematicDescriptor、MetadataDescriptor 和 StatisticsDescriptor

针对 ExternalCatalog 的问题,Flink 社区提出了一套全新的 Catalog 接口(new Catalog API)来取代现有的 ExternalCatalog。新的 Catalog 实现的功能包括:

  • 能够支持数据库、表、分区等多种元数据对象
  • 允许在一个用户 Session 中维护多个 Catalog 实例,从而支持同时访问多个外部系统
  • Catalog 以可插拔的方式接入 Flink,允许用户提供自定义的实现

下图展示了新的 Catalog API 的总体架构:

创建 TableEnvironment 的时候会同时创建一个 CatalogManager,负责管理不同的 Catalog 实例。TableEnvironment 通过 Catalog 来为 Table API 和 SQL Client 用户提供元数据服务。

val settings = EnvironmentSettings.newInstance().useBlinkPlanner().inBatchMode().build()val tableEnv = TableEnvironment.create(settings)
val name            = "myhive"
val defaultDatabase = "mydatabase"
val hiveConfDir     = "/opt/hive-conf"// a local path
val version         = "2.3.4"val hive = newHiveCatalog(name, defaultDatabase, hiveConfDir, version)
tableEnv.registerCatalog("myhive", hive)// set the HiveCatalog as the current catalog of the session
tableEnv.useCatalog("myhive")

目前 Catalog 有两个实现,GenericInMemoryCatalog 和 HiveCatalog。其中 GenericInMemoryCatalog 保持了原有的 Flink 元数据管理机制,将所有元数据保存在内存中。而 HiveCatalog 会与一个 Hive Metastore 的实例连接,提供元数据持久化的能力。要使用 Flink 与 Hive 进行交互,用户需要配置一个 HiveCatalog,并通过 HiveCatalog 访问 Hive 中的元数据。

另一方面,HiveCatalog 也可以用来处理 Flink 自身的元数据,在这种场景下,HiveCatalog 仅将 Hive Metastore 作为持久化存储使用,写入 Hive Metastore 中的元数据并不一定是 Hive 所支持的格式。一个 HiveCatalog 实例可以同时支持这两种模式,用户无需为管理 Hive 和 Flink 的元数据创建不同的实例。

另外,通过设计 HiveShim 来支持不同版本的 Hive Metastore,具体支持的 Hive 版本列表,请参考官方文档。

表数据

Flink 提供了 Hive Data Connector 来读写 Hive 的表数据。Hive Data Connector 尽可能的复用了 Hive 本身的 Input/Output Format 和 SerDe 等类,这样做的好处一方面是减少了代码重复,更重要的是可以最大程度的保持与 Hive 的兼容,即 Flink 写入的数据 Hive 可以正常读取,并且反之亦然。

集成 Hive 功能

Flink 与 Hive 集成的功能在 1.9.0 版本中作为试用功能发布,存在不少使用的局限性,但是不久将发布的 Flink 1.10 稳定版本会更加完善集成 Hive 的功能并应用到企业场景中。

为了让读者提前体验 Flink 1.10 集成 Hive 的功能,笔者会基于 Cloudera CDH 编译 Flink 1.10.0 RC1 版本并进行较为完整的测试。

环境信息

CDH 版本:cdh5.16.2
Flink 版本:release-1.10.0-rc1

Flink 使用了 RC 版本,仅供测试,不建议用于生产环境。
目前 Cloudera Data Platform 正式集成了 Flink 作为其流计算产品,非常方便用户使用。

CDH 环境开启了 Sentry 和 Kerberos。

下载并编译 Flink

$ wget https://github.com/apache/flink/archive/release-1.10.0-rc1.tar.gz
$ tar zxvf release-1.10.0-rc1.tar.gz
$ cd flink-release-1.10.0-rc1/
$ mvn clean install -DskipTests-Pvendor-repos -Dhadoop.version=2.6.0-cdh5.16.2

不出意外的话,编译到 flink-hadoop-fs 模块时,会报如下错误:

[ERROR] Failed to execute goal on project flink-hadoop-fs: Could not resolve dependencies for project org.apache.flink:flink-hadoop-fs:jar:1.10.0: Failed to collect dependencies at org.apache.flink:flink-shaded-hadoop-2:jar:2.6.0-cdh5.16.2-9.0: Failed to read artifact descriptor for org.apache.flink:flink-shaded-hadoop-2:jar:2.6.0-cdh5.16.2-9.0: Could not transfer artifact org.apache.flink:flink-shaded-hadoop-2:pom:2.6.0-cdh5.16.2-9.0 from/to HDPReleases (https://repo.hortonworks.com/content/repositories/releases/): Remote host closed connection during handshake: SSL peer shut down incorrectly

编译中遇到 flink-shaded-hadoop-2 找不到的问题,其实查看 Maven 仓库会发现,根本原因是 CDH 的 flink-shaded-hadoop-2 的 jar 包在 Maven 中央仓库是没有对应的编译版本,所以需要先对 Flink 依赖的 flink-shaded-hadoop-2 进行打包,再进行编译。

■ 解决 flink-shaded-hadoop-2 问题

  • 获取 flink-shaded 源码
git clone https://github.com/apache/flink-shaded.git
  • 切换依赖的版本分支

根据上面报错时提示缺少的版本切换对应的代码分支,即缺少的是 9.0 版本的 flink-shaded-hadoop-2:

git checkout release-9.0
  • 配置 CDH Repo 仓库

修改 flink-shaded 项目中的 pom.xml,添加 CDH maven 仓库,否则编译时找不到 CDH 相关的包。

在 ... 中添加如下内容:

<profile>
<id>vendor-repos</id>
<activation>
<property>
<name>vendor-repos</name>
</property>
</activation>
<!-- Add vendor maven repositories -->
<repositories>
<!-- Cloudera -->
<repository>
<id>cloudera-releases</id>
<url>https://repository.cloudera.com/artifactory/cloudera-repos</url>
<releases>
<enabled>true</enabled>
</releases>
<snapshots>
<enabled>false</enabled>
</snapshots>
</repository>
</repositories>
</profile>
  • 编译 flink-shaded

开始执行编译:

mvn clean install -DskipTests-Drat.skip=true-Pvendor-repos -Dhadoop.version=2.6.0-cdh5.16.2

建议通过科学上网方式编译,如果读者遇到一些网络连接的问题,可以试着重试或者更换依赖组件的仓库地址。

编译成功后,就会把 flink-shaded-hadoop-2-uber-2.6.0-cdh5.16.2-9.0.jar 安装在本地 maven 仓库,如下为编译的最后日志:

Installing /Users/.../source/flink-shaded/flink-shaded-hadoop-2-uber/target/flink-shaded-hadoop-2-uber-2.6.0-cdh5.16.2-9.0.jar to /Users/.../.m2/repository/org/apache/flink/flink-shaded-hadoop-2-uber/2.6.0-cdh5.16.2-9.0/flink-shaded-hadoop-2-uber-2.6.0-cdh5.16.2-9.0.jar
Installing /Users/.../source/flink-shaded/flink-shaded-hadoop-2-uber/target/dependency-reduced-pom.xml to /Users/.../.m2/repository/org/apache/flink/flink-shaded-hadoop-2-uber/2.6.0-cdh5.16.2-9.0/flink-shaded-hadoop-2-uber-2.6.0-cdh5.16.2-9.0.pom

重新编译 Flink

mvn clean install -DskipTests-Pvendor-repos -Dhadoop.version=2.6.0-cdh5.16.2

漫长的等待过程,读者可以并行做其他事情。

编译过程中,如果不出意外的话,会看到类似下面的错误信息:

[INFO] Running 'npm ci --cache-max=0 --no-save' in /Users/xxx/Downloads/Flink/flink-release-1.10.0-rc1/flink-release-1.10.0-rc1/flink-runtime-web/web-dashboard [WARNING] npm WARN prepare removing existing node_modules/ before installation [ERROR] WARN registry Unexpected warning for https://registry.npmjs.org/: Miscellaneous Warning ECONNRESET: request to https://registry.npmjs.org/mime/-/mime-2.4.0.tgz failed, reason: read ECONNRESET [ERROR] WARN registry Using stale package data from https://registry.npmjs.org/ due to a request error during revalidation. [ERROR] WARN registry Unexpected warning for https://registry.npmjs.org/: Miscellaneous Warning ECONNRESET: request to https://registry.npmjs.org/optimist/-/optimist-0.6.1.tgz failed, reason: read ECONNRESET

可以看到, flink-runtime-web 模块引入了对 frontend-maven-plugin 的依赖,需要安装 node、npm 和依赖组件。

如果没有通过科学上网,可以修改 flink-runtime-web/pom.xml 文件,添加 nodeDownloadRoot 和 npmDownloadRoot 的信息:

<plugin>
<groupId>com.github.eirslett</groupId>
<artifactId>frontend-maven-plugin</artifactId>
<version>1.6</version>
<executions>
<execution>
<id>install node and npm</id>
<goals>
<goal>install-node-and-npm</goal>
</goals>
<configuration>
<nodeDownloadRoot>https://registry.npm.taobao.org/dist/</nodeDownloadRoot>
<npmDownloadRoot>https://registry.npmjs.org/npm/-/</npmDownloadRoot>
<nodeVersion>v10.9.0</nodeVersion>
</configuration>
</execution>
<execution>
<id>npm install</id>
<goals>
<goal>npm</goal>
</goals>
<configuration>
<arguments>ci --cache-max=0 --no-save</arguments>
<environmentVariables>
<HUSKY_SKIP_INSTALL>true</HUSKY_SKIP_INSTALL>
</environmentVariables>
</configuration>
</execution>
<execution>
<id>npm run build</id>
<goals>
<goal>npm</goal>
</goals>
<configuration>
<arguments>run build</arguments>
</configuration>
</execution>
</executions>
<configuration>
<workingDirectory>web-dashboard</workingDirectory>
</configuration>
</plugin>

编译成功后,Flink 安装文件位于 flink-release-1.10.0-rc1/flink-dist/target/flink-1.10.0-bin 目录下,打包并上传到部署到节点:

$ cd flink-dist/target/flink-1.10.0-bin
$ tar zcvf flink-1.10.0.tar.gz flink-1.10.0

部署和配置

Flink 部署比较简单,解压缩包即可。另外可以设置软链接、环境变量等,笔者不再介绍。

Flink 的核心配置文件是 flink-conf.yaml,一个典型的配置如下:

jobmanager.rpc.address: localhost
jobmanager.rpc.port: 6123
jobmanager.heap.size: 2048m
taskmanager.heap.size: 1024m
taskmanager.numberOfTaskSlots: 4
parallelism.default: 1
high-availability: zookeeper
high-availability.storageDir:hdfs:///user/flink110/recovery
high-availability.zookeeper.quorum: zk1:2181,zk2:2181,zk3:2181
state.backend: filesystem
state.checkpoints.dir: hdfs:///user/flink110/checkpoints
state.savepoints.dir:hdfs:///user/flink110/savepoints
jobmanager.execution.failover-strategy: region
rest.port: 8081
taskmanager.memory.preallocate: false
classloader.resolve-order: parent-first
security.kerberos.login.use-ticket-cache: true
security.kerberos.login.keytab:/home/flink_user/flink_user.keytab
security.kerberos.login.principal: flink_user
jobmanager.archive.fs.dir:hdfs:///user/flink110/completed-jobs
historyserver.web.address: 0.0.0.0
historyserver.web.port: 8082
historyserver.archive.fs.dir:hdfs:///user/flink110/completed-jobs
historyserver.archive.fs.refresh-interval: 10000笔者只罗列了一些常见的配置参数,读者根据实际情况修改。配置参数其实还是比较容易理解的,以后结合实战的文章再进行详细讲解。**■  集成 Hive 配置的依赖**如果要使用 Flink 与 Hive 集成的功能,除了上面的配置外,用户还需要添加相应的依赖:- 如果需要使用 SQL Client,则需要将依赖的 jar 拷贝到 Flink 的 lib 目录中
- 如果需要使用 Table API,则需要将相应的依赖添加到项目中(如 pom.xml)

org.apache.flink
flink-connector-hive_2.11
1.11-SNAPSHOT
provided

org.apache.flink
flink-table-api-java-bridge_2.11
1.11-SNAPSHOT
provided

org.apache.hive
hive-exec
${hive.version}
provided


笔者主要介绍使用 SQL Client 的方式,由于使用的 CDH 版本为 5.16.2,其中 Hadoop 版本为 2.6.0,Hive 版本为 1.1.0,所以需要将如下 jar 包拷贝到 flink 部署家目录中的 lib 目录下:- Flink 的 Hive connectorflink-connector-hive2.11-1.10.0.jar
flink-hadoop-compatibility2.11-1.10.0.jar
flink-orc_2.11-1.10.0.jar

flink-release-1.10.0-rc1/flink-connectors/flink-hadoop-compatibility/target/flink-hadoop-compatibility_2.11-1.10.0.jar
flink-release-1.10.0-rc1/flink-connectors/flink-connector-hive/target/flink-connector-hive_2.11-1.10.0.jar
flink-release-1.10.0-rc1/flink-formats/flink-orc/target/flink-orc_2.11-1.10.0.jar


- Hadoop 依赖flink-shaded-hadoop-2-uber-2.6.0-cdh5.16.2-9.0.jar

flink-shaded/flink-shaded-hadoop-2-uber/target/flink-shaded-hadoop-2-uber-2.6.0-cdh5.16.2-9.0.jar

  • Hive 依赖

hive-exec-1.1.0-cdh5.16.2.jar
hive-metastore-1.1.0-cdh5.16.2.jar
libfb303-0.9.3.jar

/opt/cloudera/parcels/CDH/lib/hive/lib/hive-exec-1.1.0-cdh5.16.2.jar
/opt/cloudera/parcels/CDH/lib/hive/lib/hive-metastore-1.1.0-cdh5.16.2.jar
/opt/cloudera/parcels/CDH/lib/hive/lib/libfb303-
0.9.3.jar

其中 flink-shaded-hadoop-2-uber 包含了 Hive 对于 Hadoop 的依赖。如果不用 Flink 提供的包,用户也可以将集群中使用的 Hadoop 包添加进来,不过需要保证添加的 Hadoop 版本与 Hive 所依赖的版本是兼容的。

依赖的 Hive 包(即 hive-exec 和 hive-metastore)也可以使用用户集群中 Hive 所提供的 jar 包,详情请见支持不同的 Hive 版本。

Flink 部署的节点要添加 Hadoop、Yarn 以及 Hive 的客户端。

■ 配置 HiveCatalog

多年来,Hive Metastore 在 Hadoop 生态系统中已发展成为事实上的元数据中心。许多公司在其生产中有一个单独的 Hive Metastore 服务实例,以管理其所有元数据(Hive 元数据或非 Hive 元数据)。

如果同时部署了 Hive 和 Flink,那么通过 HiveCatalog 能够使用 Hive Metastore 来管理 Flink 的元数据。

如果仅部署 Flink,HiveCatalog 就是 Flink 开箱即用提供的唯一持久化的 Catalog。如果没有持久化的 Catalog,那么使用 Flink SQL CREATE DDL 时必须在每个会话中重复创建像 Kafka 表这样的元对象,这会浪费大量时间。HiveCatalog 通过授权用户只需要创建一次表和其他元对象,并在以后的跨会话中非常方便地进行引用和管理。

如果要使用 SQL Client 时,用户需要在 sql-client-defaults.yaml 中指定自己所需的 Catalog,在 sql-client-defaults.yaml 的 catalogs 列表中可以指定一个或多个 Catalog 实例。

以下的示例展示了如何指定一个 HiveCatalog:

execution:planner: blinktype: streaming...current-catalog: myhive  # set the HiveCatalog as the current catalog of the sessioncurrent-database: mydatabasecatalogs:  - name: myhivetype: hivehive-conf-dir: /opt/hive-conf  # contains hive-site.xmlhive-version:2.3.4

其中:

  • name 是用户给每个 Catalog 实例指定的名字,Catalog 名字和 DB 名字构成了 FlinkSQL 中元数据的命名空间,因此需要保证每个 Catalog 的名字是唯一的。
  • type 表示 Catalog 的类型,对于 HiveCatalog 而言,type 应该指定为 hive。
  • hive-conf-dir 用于读取 Hive 的配置文件,用户可以将其设定为集群中 Hive 的配置文件目录。
  • hive-version 用于指定所使用的 Hive 版本。

指定了 HiveCatalog 以后,用户就可以启动 sql-client,并通过以下命令验证 HiveCatalog 已经正确加载。

Flink SQL> show catalogs;
default_catalog
myhiveFlink SQL> use catalog myhive;

其中 show catalogs 会列出加载的所有 Catalog 实例。需要注意的是,除了用户在 sql-client-defaults.yaml 文件中配置的 Catalog 以外,FlinkSQL 还会自动加载一个 GenericInMemoryCatalog 实例作为内置的 Catalog,该内置 Catalog 默认名字为 default_catalog。

读写 Hive 表

设置好 HiveCatalog 以后就可以通过 SQL Client 或者 Table API 来读写 Hive 中的表了。

假设 Hive 中已经有一张名为 mytable 的表,我们可以用以下的 SQL 语句来读写这张表。

■ 读数据

Flink SQL> show catalogs;
myhive
default_catalogFlink SQL> use catalog myhive;Flink SQL> show databases;
defaultFlink SQL> show tables;
mytableFlink SQL> describe mytable;
root|-- name: name
|-- type: STRING
|-- name: value
|-- type: DOUBLEFlink SQL> SELECT * FROM mytable;name      value
__________ __________Tom        4.72John       8.0    Tom        24.2Bob.       3.14    Bob        4.72    Tom        34.9    Mary       4.79    Tiff          2.72    Bill          4.33    Mary       77.7

■ 写数据

Flink SQL> INSERT INTO mytable SELECT 'Tom',25;Flink SQL> INSERT OVERWRITE mytable SELECT 'Tom', 25;# 静态分区
Flink SQL> INSERT OVERWRITE myparttable PARTITION (my_type='type_1', my_date='2019-08-08') SELECT 'Tom', 25;# 动态分区Flink SQL> INSERT OVERWRITE myparttable SELECT 'Tom', 25, 'type_1', '2019-08-08';# 静态分区和动态分区Flink SQL> INSERT OVERWRITE myparttable PARTITION (my_type='type_1') SELECT 'Tom', 25, '2019-08-08';

总结

在本文中,笔者首先介绍了 Flink 与 Hive 集成功能的架构设计,然后从源码开始编译,解决遇到的一些问题,接着部署和配置 Flink 环境以及集成 Hive 的具体操作过程,最后参考官方的案例,对 Hive 表进行读写操作。

后续,笔者会结合生产环境的实际使用情况,讲解通过 Flink SQL 来操作 Hive。

参考:

  • https://ci.apache.org/projects/flink/flink-docs-release-1.10/flinkDev/building.html
  • https://ververica.cn/developers/flink1-9-hive/

原文链接
本文为云栖社区原创内容,未经允许不得转载。

Hive 终于等来了 Flink相关推荐

  1. surfacepro3运行C语言,终于等来USB-C接口!微软 发布 Surface Pro 7 与 Surface Laptop 3 笔记本电脑...

    终于等来USB-C接口!微软 发布 Surface Pro 7 与 Surface Laptop 3 笔记本电脑5788元起,Surface Laptop 3采用AMD方案 2019-10-03 16 ...

  2. 鸿蒙系统的研发者是东南大学,终于等来了!华为副总裁官宣,3月31日这天,将载入华为历史...

    本文原创,请勿抄袭和搬运,违者必究 华为副总裁正式官宣 华为对鸿蒙的布局已经进入到关键阶段,因为自从去年发布鸿蒙手机开发者Beta版本以后,外界就在期待鸿蒙手机系统的正式到来. 在此之前花粉和国人无不 ...

  3. 终于等来《仙剑奇侠传四》,全新阵容太可了!

    终于等来<仙剑奇侠传四>,全新阵容太可了!还好我没有放弃...... <仙剑奇侠传三>,全新阵容太可了! 已经过去十五年了,就连<仙剑奇侠传三>都是十一年前的事了, ...

  4. 小知识点:ARM 架构 Linux 大数据集群基础环境搭建(Hadoop、MySQL、Hive、Spark、Flink、ZK、Kafka、Nginx、Node)

      换了 M2 芯片的 Mac,以前 x86 版本的 Linux 大数据集群基础环境搭建在 ARM 架构的虚拟机集群上有些用不了了,现在重新写一份基于 ARM 架构的,少数不兼容之外其他都差不多,相当 ...

  5. 【第98期】终于有人把Flink设计理念与基本架构讲明白了

    导读:本文从设计理念的角度将Flink 与主流计算引擎 Hadoop MapReduce和Spark进行对比,并从宏观上介绍Flink的基本架构. 01 Flink与主流计算引擎对比 1. Hadoo ...

  6. 终于等来了十一长假,当然要戴上你去这些美到哭的地方

    十一小长假马上就要到了,想必小伙伴们已经摩拳擦掌的准备好好利用小长假去浪了吧? 作为一个中国人,毫不客气自豪地说:我们伟大的祖国,地大物博,大好河山.金秋十月,国庆长假,适合玩的地方挺多.从一个小驴的 ...

  7. Flink 与 Hive 的磨合期

    有不少读者反馈,参考上篇文章<Hive 终于等来了 Flink>部署 Flink 并集成 Hive 时,出现一些 bug 以及兼容性等问题.虽已等来,却未可用.所以笔者增加了这一篇文章,作 ...

  8. cdh hive on spark_Flink 与 Hive 的磨合期

    有不少读者反馈,参考上篇文章<Hive 终于等来了 Flink>部署 Flink 并集成 Hive 时,出现一些 bug 以及兼容性等问题.虽已等来,却未可用.所以笔者增加了这一篇文章,作 ...

  9. 年度盘点!Flink 社区全年的精华内容都在这里啦(内附福利)

    转眼间,2020年悄然落幕.这一年,Flink 社区高速发展繁荣,我们发布了三个版本,举办了 40+ 线上线下活动,推送了 100+ 技术干货与最佳实践.新的一年开启之时,社区从年度最佳实践.核心技术 ...

最新文章

  1. 了解JavaScript 对象的属性操作
  2. Effective Java之必要时进行保护性拷贝(三十九)
  3. Java并发中常用同步工具类
  4. 485通讯转换器产品功能特点介绍
  5. Arduino笔记-有源蜂鸣器结合开关(多瑞咪发声)
  6. ssas报表项目数据集_Analysis Services(SSAS)多维设计技巧–数据源视图和多维数据集
  7. 华为手机上的网上邻居怎么用_只要华为手机用上鸿蒙OS2.0,刚买的手机我也马上换!...
  8. linux无法启动hbase密码,linux – 无法在请求的2181端口启动ZK,而导出HBASE_MANAGES_ZK = false...
  9. psenet的eval_ctw1500.py解析
  10. 热烈庆祝阳光网驿-行业软件交流平台与北京汉邦极通科技有限公司成功合作
  11. php无限分类算法,php递归算法 php递归函数无限级分类
  12. wifi信号桥怎么设置_手机设置路由器WDS桥连方法
  13. 20162327WJH 实验三 《敏捷开发与XP实践》 实验报告
  14. 弹性公网IP、私有IP、浮动IP、虚拟IP之间有何区别?
  15. 红帽linux系统内核版本7,如何查看Linux发行版内核版本及系统版本?
  16. 微擎服务器数据迁移 ,微擎通过迁移数据方式搬家换服务器换站点换域名【图文教程】
  17. PLC 变频器、触摸屏综合实训平台
  18. FPGA数字时钟(可暂停调数,含代码)
  19. 公司股权分配方案 (2)
  20. 策略死守“传统数据”招招落于人后?-也许您需要另类数据

热门文章

  1. 12v小型电机型号大全_电机型号参数大全
  2. python中math模块函数_Python常用的一些内建函数和math模块函数
  3. java中exception_Java中的异常 Exceptions
  4. adam算法效果差原因_干货|快来get中央空调冬天制热效果差的十大原因!
  5. 【LeetCode笔记】155. 最小栈(Java、栈)
  6. 概要设计说明书_没有什么比牙签更好的设计了
  7. python process_Python Process/Thread 概念整理
  8. leetcode 4 --- 寻找两个有序数组的中位数
  9. linux服务器组件有哪些,推荐几个linux服务器面板
  10. net应用程序中发生了未经处理的异常怎么办_介绍一些在.NET Core 3.0中引入的诊断改进工具...