Android 支持库迁移到AndroidX

news2024/11/22 10:32:26

对应官方文档:
developer.android.com/jetpack/and…

简单点说就是,对App开发者而言,AndroidX更加友好,因为我们引入时,只需要关注AndroidX中具体的需要引入的构件版本即可。且大部分具体的构件,具有一致的版本号。开发者使用起来不再需要关注项目自身的最低支持版本和编译版本了,只需要像引入其他的第三方库一样,v1.0、v2.0、v3.0这种方式引入即可。

如原有的引入写法
com.android.support:recyclerview-v7:28.0.0
变成了
androidx.recyclerview:recyclerview:1.0.0

官方文档也提供了Androidx版本具体的升级日志记录。
developer.android.com/jetpack/and… developer.android.com/jetpack/and…

三、支持库迁移到AndroidX

3.1 迁移AndroidX的必要性

AndroidX对开发者使用更加友好,同时,支持库文档上官方已经明确支持库后续不再维护。另外,在Android Studio上新建模块时,也发现如果没有迁移到AndroidX,模块创建不了,表明开始有强制性的措施使得开发者必须迁移到AndroidX。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

3.2 迁移AndroidX的前置条件

Android Sudio在3.2版本开始,对直接迁移到AndroidX进行了支持。在操作路径Refactor > Migrate to AndroidX下,但使用时会发现可能存在如下提示:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

这也说明了,利用官方内置的迁移方式迁移AndroidX之前,工程环境上最好满足如下条件:
1,Android Studio 3.2及以上。当前时点最新版本已经是3.5稳定版了。
2,AGP版本3.2.0及以上,对应的Gradle版本4.6及以上。
3,项目编译版本28及以上。

如果当前项目没有满足上述条件,可以先升级对应的配套。

3.3 迁移过程

Android官方提供了具体的迁移指引。具体参见文档:
developer.android.com/jetpack/and…

Just Start!

以下主要记录实际项目中的迁移过程,以及遇到的问题及解决。

Refactor > Migrate to AndroidX操作后,AS会有对应的迁移提醒,提示你去备份项目文件,如有必要可以先备份。但一般而言,AS项目都是基于Git进行管理,直接单独切一个分支进行迁移操作即可,此处备份成zip现实意义不大。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

点击Migrate后,会出现弹窗Looking for Usages,开始在当前项目中搜索所有可能需要迁移的源文件,包括代码源文件、XML文件、build.gradle配置文件等,最终会列出当前主工程使用到支持库的所有文件列表。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

点击Do Refactor确认迁移,AS自动执行迁移AndroidX的替换过程。如将对应的支持库类名、包名、构件名等都替换成相应的AndroidX形式。

一点时间后,主工程替换完成。此时打开gradle.properties,会发现自动添加了如下配置项。

android.useAndroidX=true
android.enableJetifier=true

android.useAndroidX=true,表示主工程使用AndroidX形式。
android.enableJetifier=true,表示针对主工程中使用到的三方库,也会自动执行AndroidX的替换过程。

同时,在自动执行三方库的替换时,出下了如下报错信息:

ERROR: Unable to resolve dependency for ‘:MyCorn@prodDebug/compileClasspath’: Failed to transform file ‘fingerprint-1.1.1.aar’ to match attributes {artifactType=processed-aar} using transform JetifyTransform

大致的意思是使用JetifyTransformfingerprint-1.1.1.aar进行替换过程中,出现了问题。但具体问题没有进一步的提示信息。于是,直接通过命令执行下构建看一下:

./gradlew assembleDevDebug

1: Task failed with an exception.

  • What went wrong:
    Could not resolve all files for configuration ‘:MyCorn:devDebugCompileClasspath’.

Failed to transform file ‘fingerprint-1.1.1.aar’ to match attributes {artifactType=processed-aar} using transform JetifyTransform
Failed to transform ‘/Users/corn/.gradle/caches/modules-2/files-2.1/com.corn.feature/fingerprint/1.1.1/ae2da4c824fb2923eac7a1340222d50d6308f7ea/fingerprint-1.1.1.aar’ using Jetifier. Reason: 8. (Run with --stacktrace for more details.) To disable Jetifier, set android.enableJetifier=false in your gradle.properties file.

进而,带上–stacktrace看看。

./gradlew assembleDevDebug --stacktrace


Caused by: java.lang.ArrayIndexOutOfBoundsException: 8
at org.objectweb.asm.ClassReader.readFrameType(ClassReader.java:2313)
at org.objectweb.asm.ClassReader.readFrame(ClassReader.java:2269)
at org.objectweb.asm.ClassReader.readCode(ClassReader.java:1448)
at org.objectweb.asm.ClassReader.readMethod(ClassReader.java:1126)
at org.objectweb.asm.ClassReader.accept(ClassReader.java:698)
at org.objectweb.asm.ClassReader.accept(ClassReader.java:500)
at com.android.tools.build.jetifier.processor.transform.bytecode.ByteCodeTransformer.runTransform(ByteCodeTransformer.kt:39)
at com.android.tools.build.jetifier.processor.Processor.visit(Processor.kt:328)
at com.android.tools.build.jetifier.processor.archive.ArchiveFile.accept(ArchiveFile.kt:41)
at com.android.tools.build.jetifier.processor.Processor.visit(Processor.kt:316)
at com.android.tools.build.jetifier.processor.archive.Archive.accept(Archive.kt:66)
at com.android.tools.build.jetifier.processor.Processor.visit(Processor.kt:316)
at com.android.tools.build.jetifier.processor.archive.Archive.accept(Archive.kt:66)
at com.android.tools.build.jetifier.processor.Processor.transformLibrary(Processor.kt:312)
at com.android.tools.build.jetifier.processor.Processor.transform(Processor.kt:175)
at com.android.build.gradle.internal.dependency.JetifyTransform.transform(JetifyTransform.kt:199)
… 39 more

我们发现,JetifyTransform内部使用了ASM,在对aar进行ClassReader的过程中抛出了异常。并且从错误栈信息上看,应该有一类叫jetifier的工具,是在这个工具中调用的ASM操作。

官方文档搜索下,果然发现了jetifier的踪迹。
developer.android.com/studio/comm…

同样的,Google Source上也找到了其对应的实现。
android.googlesource.com/platform/fr…

下载对应的jetifier-standalone,解压后,执行命令对fingerprint-1.1.1.aar执行AndroidX转化。

➜ bin ./jetifier-standalone -i ./fingerprint-1.1.1.aar -o 11.aar
Exception in thread “main” java.lang.ArrayIndexOutOfBoundsException: 8
at org.objectweb.asm.ClassReader.readFrameType(ClassReader.java:2313)
at org.objectweb.asm.ClassReader.readFrame(ClassReader.java:2269)
at org.objectweb.asm.ClassReader.readCode(ClassReader.java:1448)
at org.objectweb.asm.ClassReader.readMethod(ClassReader.java:1126)
at org.objectweb.asm.ClassReader.accept(ClassReader.java:698)
at org.objectweb.asm.ClassReader.accept(ClassReader.java:500)
at com.android.tools.build.jetifier.processor.transform.bytecode.ByteCodeTransformer.runTransform(ByteCodeTransformer.kt:40)
at com.android.tools.build.jetifier.processor.Processor.visit(Processor.kt:539)
at com.android.tools.build.jetifier.processor.archive.ArchiveFile.accept(ArchiveFile.kt:53)
at com.android.tools.build.jetifier.processor.Processor.visit(Processor.kt:521)
at com.android.tools.build.jetifier.processor.archive.Archive.accept(Archive.kt:76)
at com.android.tools.build.jetifier.processor.Processor.visit(Processor.kt:521)
at com.android.tools.build.jetifier.processor.archive.Archive.accept(Archive.kt:76)
at com.android.tools.build.jetifier.processor.Processor.transformLibrary(Processor.kt:517)
at com.android.tools.build.jetifier.processor.Processor.transform2(Processor.kt:291)
at com.android.tools.build.jetifier.processor.Processor.transform2 d e f a u l t ( P r o c e s s o r . k t : 251 ) a t c o m . a n d r o i d . t o o l s . b u i l d . j e t i f i e r . s t a n d a l o n e . M a i n . r u n ( M a i n . k t : 156 ) a t c o m . a n d r o i d . t o o l s . b u i l d . j e t i f i e r . s t a n d a l o n e . M a i n default(Processor.kt:251) at com.android.tools.build.jetifier.standalone.Main.run(Main.kt:156) at com.android.tools.build.jetifier.standalone.Main default(Processor.kt:251)atcom.android.tools.build.jetifier.standalone.Main.run(Main.kt:156)atcom.android.tools.build.jetifier.standalone.MainCompanion.main(Main.kt:109)
at com.android.tools.build.jetifier.standalone.Main.main(Main.kt)

发现出现了同样的错误信息。

显然,应该是fingerprint-1.1.1.aar中有字节码有问题。经查,fingerprint内部直接以jar方式引入了三星的指纹识别库,已经很比较老的版本了,经业务同学确认,现在已经可以直接去除。

去除fingerprint内部的三星指纹库后,升级版本,下载对应的aar文件后,再次尝试转化:

./jetifier-standalone -i ./fingerprint-1.1.3-20190916.092208-1.aar -o mm.aar

执行成功,且有转换后的对应文件生成。

主工程更新fingerprint对应依赖版本后,重新执行构建,出现错误提示:

e: /Users/corn/AndroidStudioProjects/MyCorn/base/src/main/java/com/mycorn/base/mvvm/EventLiveData.kt: (13, 5): ‘observe’ overrides nothing
e: /Users/corn/AndroidStudioProjects/MyCorn/base/src/main/java/com/mycorn/base/mvvm/EventLiveData.kt: (20, 5): ‘removeObserver’ overrides nothing

原因在于对应的LiveData接口observe、removeObserver中的形参有所改动,从原来的

@NonNull Observer observer

变成了

@NonNull Observer<? super T> observer

修正EventLiveData类中的重写方法的对应形参,与接口保持一致即可。

再次重新构建,出现错误信息:

/Users/corn/AndroidStudioProjects/MyCorn/trans/src/main/java/com/mycorn/biz/supertrans/v12/slide/ItemSlideHelper.java:566: 错误: 程序包androidx.appcompat.recyclerview.R不存在
.getDimension(androidx.appcompat.recyclerview.R.dimen.item_touch_helper_swipe_escape_velocity);

/Users/corn/AndroidStudioProjects/MyCorn/trans/src/main/java/com/mycorn/biz/supertrans/v12/slide/ItemSlideHelper.java:568: 错误: 程序包androidx.appcompat.recyclerview.R不存在
.getDimension(androidx.appcompat.recyclerview.R.dimen.item_touch_helper_swipe_escape_max_velocity);

/Users/corn/AndroidStudioProjects/MyCorn/trans/src/main/java/com/mycorn/biz/supertrans/v12/slide/ItemSlideHelper.java:2115: 错误: 程序包androidx.appcompat.recyclerview.R不存在
androidx.appcompat.recyclerview.R.dimen.item_touch_helper_max_drag_scroll_per_frame);

核查官方文档,对应的替换关系应该是:

ndroid.support.v7.recyclerview.R

替换为

androidx.recyclerview.R

此处替换成了

androidx.appcompat.recyclerview.R

按照文档对应修正过来。

再次重新构建,可以构建成功。

3.4 核验与发现

此时构建成功,是不是就真的都处理好了呢,是不是都没问题了呢。显然不是的。

首先,分别查看主工程对应的编译时和运行时依赖,看看是否都从android.support.* 替换成了androidx.*

./gradlew -q MyCorn:dependencies --configuration devDebugAndroidTestCompileClasspath > ~/compile.txt

./gradlew -q MyCorn:dependencies --configuration devDebugAndroidTestRuntimeClasspath > ~/runtime.txt

仔细对比后发现,虽然依赖中都已经被替换成了androidx.* 。但编译时的依赖中含有大量的rc01。如:

androi
dx.appcompat:appcompat:1.0.0-rc01
androidx.recyclerview:recyclerview:1.0.0-rc01

但运行时依赖中却没有rc01

androidx.appcompat:appcompat:1.0.0
androidx.recyclerview:recyclerview:1.0.0

经核查后发现,主工程中之前依赖支持库时有两种写法,一种是直接写法,如:

implementation 'com.android.support:appcompat-v7:28.0.0

另一种是采取统一定义后,进行的变量形式引入:

api rootProject.ext.dependencies[“appcompat-v7”]

其中,具体变量,如appcompat-v7被统一定义在了专用的一个dependencies.gradle文件中。
大致形式如下:

// 统一配置管理
def supportVersion = “28.0.0”

project.ext {
android = [
“compileSdkVersion”: 28,
“minSdkVersion” : 19,
“targetSdkVersion” : 26,
“javaMaxHeapSize” : “5G”
]

dependencies = [
“support-compat” : “com.android.support:support-compat: s u p p o r t V e r s i o n " , " s u p p o r t − c o r e − u t i l s " : " c o m . a n d r o i d . s u p p o r t : s u p p o r t − c o r e − u t i l s : {supportVersion}", "support-core-utils" : "com.android.support:support-core-utils: supportVersion","supportcoreutils":"com.android.support:supportcoreutils:{supportVersion}”,
“support-core-ui” : “com.android.support:support-core-ui: s u p p o r t V e r s i o n " , " s u p p o r t − m e d i a − c o m p a t " : " c o m . a n d r o i d . s u p p o r t : s u p p o r t − m e d i a − c o m p a t : {supportVersion}", "support-media-compat": "com.android.support:support-media-compat: supportVersion","supportmediacompat":"com.android.support:supportmediacompat:{supportVersion}”,
“support-fragment” : “com.android.support:support-fragment: s u p p o r t V e r s i o n " , " s u p p o r t − a n n o t a t i o n s " : " c o m . a n d r o i d . s u p p o r t : s u p p o r t − a n n o t a t i o n s : {supportVersion}", "support-annotations" : "com.android.support:support-annotations: supportVersion","supportannotations":"com.android.support:supportannotations:{supportVersion}”,
“appcompat-v7” : “com.android.support:appcompat-v7:${supportVersion}”,


]
}

来到对应的文件,发现对应的android.support.*并没有被替换成androidx.*

而在build.gralde中直接引入的写法,是被相应替换了的。已经被正确替换成了:

implementation ‘androidx.appcompat:appcompat:1.0.0’

也就是说,构建时,遇到api rootProject.ext.dependencies["appcompat-v7"],其实是没有被准确识别的,按照编译时的依赖关系,最终被识别成了带有rc01的AndroidX版本。

于是,才出现了编译时和运行时大量的版本不一致情况。

解决起来很简单,直接在dependencies.gradle文件中,将android.support.*对应人为替换成androidx.*形式,并重新规范命名和版本,相应修正对应的被使用到的地方,并修正成统一的AndroidX依赖写法。

// 统一配置管理
def androidXVersion = “1.0.0”

project.ext {
android = [
“compileSdkVersion”: 28,
“minSdkVersion” : 19,
“targetSdkVersion” : 26,
“javaMaxHeapSize” : “5G”
]

dependencies = [
“androidx-core” : “androidx.core:core: a n d r o i d X V e r s i o n " , " a n d r o i d x − c o r e − u t i l s " : " a n d r o i d x . l e g a c y : l e g a c y − s u p p o r t − c o r e − u t i l s : {androidXVersion}", "androidx-core-utils" : "androidx.legacy:legacy-support-core-utils: androidXVersion","androidxcoreutils":"androidx.legacy:legacysupportcoreutils:{androidXVersion}”,
“androidx-core-ui” : “androidx.legacy:legacy-support-core-ui: a n d r o i d X V e r s i o n " , " a n d r o i d x − m e d i a " : " a n d r o i d x . m e d i a : m e d i a : {androidXVersion}", "androidx-media" : "androidx.media:media: androidXVersion","androidxmedia":"androidx.media:media:{androidXVersion}”,
“androidx-fragment” : “androidx.fragment:fragment: a n d r o i d X V e r s i o n " , " s u p p o r t − a n n o t a t i o n s " : " a n d r o i d x . a n n o t a t i o n : a n n o t a t i o n : {androidXVersion}", "support-annotations" : "androidx.annotation:annotation: androidXVersion","supportannotations":"androidx.annotation:annotation:{androidXVersion}”,
“androidx-appcompat” : “androidx.appcompat:appcompat:${androidXVersion}”,


]
}

重新输出编译时和运行时依赖,发现此时支持库版本已经一致。

重新构建项目,发现可以构建成功。

但到此时,我们依然有四个问题需要进一步确认:
1,主工程中是否有支持库相关的一些特别的写法,结果会跟上面的dependencies.gradle一样,不能被自动识别并迁移?例如反射?字符串?甚至字符串拼接?等等。

2,原有依赖库android.support.*肯定会有一些混淆配置,现在迁移成androidx.*后,混淆配置这块如何对应处理?

droidx-appcompat" : “androidx.appcompat:appcompat:${androidXVersion}”,


]
}

重新输出编译时和运行时依赖,发现此时支持库版本已经一致。

重新构建项目,发现可以构建成功。

但到此时,我们依然有四个问题需要进一步确认:
1,主工程中是否有支持库相关的一些特别的写法,结果会跟上面的dependencies.gradle一样,不能被自动识别并迁移?例如反射?字符串?甚至字符串拼接?等等。

2,原有依赖库android.support.*肯定会有一些混淆配置,现在迁移成androidx.*后,混淆配置这块如何对应处理?

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1830041.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【软件工程】【23.04】p2

关键字&#xff1a; 计算机软件定义、需求基本性质、创建系统类图所涉及的工作、RUP创建系统用况模型活动、软件生存周期模型、能力等级和成熟度等级区别联系&#xff1b; 模块结构图&#xff1a;深度宽度、扇入扇出、作用域、控制域&#xff1b; 程序流程图&#xff1a;语句…

单调栈(续)、由斐波那契数列讲述矩阵快速降幂技巧

在这里先接上一篇文章单调栈&#xff0c;这里还有单调栈的一道题 题目一&#xff08;单调栈续&#xff09; 给定一个数组arr&#xff0c; 返回所有子数组最小值的累加和 就是一个数组&#xff0c;有很多的子数组&#xff0c;每个数组肯定有一个最小值&#xff0c;要把所有子…

Golang | Leetcode Golang题解之第160题相交链表

题目&#xff1a; 题解&#xff1a; func getIntersectionNode(headA, headB *ListNode) *ListNode {if headA nil || headB nil {return nil}pa, pb : headA, headBfor pa ! pb {if pa nil {pa headB} else {pa pa.Next}if pb nil {pb headA} else {pb pb.Next}}retu…

Wifi通信协议:WEP,WPA,WPA2,WPA3,WPS

前言 无线安全性是保护互联网安全的重要因素。连接到安全性低的无线网络可能会带来安全风险&#xff0c;包括数据泄露、账号被盗以及恶意软件的安装。因此&#xff0c;利用合适的Wi-Fi安全措施是非常重要的&#xff0c;了解WEP、WPA、WPA2和WPA3等各种无线加密标准的区别也是至…

短URL服务设计

引言 在营销系统里&#xff0c;为了增加系统的活跃用户数&#xff0c;经常会有各种各样的营销活动。这类活动几乎都是为了充分利用存量用户的价值&#xff0c;促使他们分享产品或App以达到触达到更多用户的目的。又或者是出于营销目的&#xff0c;群发优惠券触达短信这种场景。…

如何将扫描的 PDF 转换为 Word

您是否正在寻找一种可靠且轻松的方式将扫描的 PDF 文档转换为可编辑的 Word 文件&#xff1f;要将 PDF 转换为可编辑的 Word 文档&#xff0c;神奇之处在于光学字符识别(OCR)。 使用 PDFgear&#xff0c;您可以无缝地将扫描的 PDF 转换为 Word&#xff0c;无论是在线还是离线。…

nginx+tomcat+nfs →web集群部署

nginxtomcatnfs →web集群部署 一.安装前介绍 NGINX是一个高性能的Web服务器和反向代理服务器。它能够处理静态内容&#xff0c;缓存请求结果&#xff0c;以及将请求转发给后端服务器。通过反向代理&#xff0c;NGINX能够实现请求的负载均衡、安全性增强、SSL加密等功能。此外…

k8s上使用ConfigMap 和 Secret

使用ConfigMap 和 Secret 实验目标&#xff1a; 学习如何使用 ConfigMap 和 Secret 来管理应用的配置。 实验步骤&#xff1a; 创建一个 ConfigMap 存储应用配置。创建一个 Secret 存储敏感信息&#xff08;如数据库密码&#xff09;。在 Pod 中挂载 ConfigMap 和 Secret&am…

youlai-boot项目的学习—工程构建与运行

开发环境 系统:mac OS Ventura 13.2.1 终端: item2 Homebrew: 4.3.5 IDE: IntelliJ IDEA 2024.1.1 (Ultimate Edition) 代码分支 仓库&#xff1a;https://gitee.com/youlaiorg/youlai-boot.git 分支&#xff1a; master commit: 9a753a2e94985ed4cbbf214156ca035082e02723 …

【工作】计算机行业相关的十六类工作简介

本文简单介绍了计算机行业相关的工作类别&#xff0c;共16种&#xff0c;包括常见招聘要求与平均工资。平均工资信息来源&#xff1a;米国企业点评职场社区glassdoor&#xff08;https://www.glassdoor.com/index.htm&#xff09; &#xff08;一&#xff09;软件工程师 软件…

FreeRtos-13资源管理

一、临界资源是什么 要独占式地访问临界资源,有3种方法: 1.公平竞争:比如使用互斥量,谁先获得互斥量谁就访问临界资源,这部分内容前面讲过。 谁要跟我抢,我就灭掉谁: 2.中断要跟我抢?我屏蔽中断 3.其他任务要跟我抢?我禁止调度器,不运行任务切换 二、暂停调度器…

STM32高级控制定时器(STM32F103):计数模式

目录 概述 1 计数模式介绍 2 加计数模式 2.1 加计数模式介绍 2.2 计数序列案例 3 减计数模式 3.1 减计数模式介绍 3.2 应用实例 4 居中对齐模式&#xff08;向上/向下计数&#xff09; 4.1 功能介绍 4.2 应用实例 概述 本文主要介绍STM32F10X定时器计数功能的相关知…

【iOS】自定义cell及其复用机制

文章目录 cell的复用注册非注册两者的区别 自定义cell cell的复用 当用户滚动 UITableView 或 UICollectionView 时,只有少量可见的 cell 会被实际创建和显示。对于那些暂时不可见的 cell,系统会将它们缓存起来以备将来复用。这就是所谓的 cell 复用机制。 为什么需要cell的复…

深度神经网络——深度学习中的 RNN 和 LSTM 是什么?

引言 自然语言处理和人工智能聊天机器人领域许多最令人印象深刻的进步都是由 递归神经网络&#xff08;RNN&#xff09; 和长短期记忆&#xff08;LSTM&#xff09;网络。 RNN 和 LSTM 是特殊的神经网络架构&#xff0c;能够处理顺序数据&#xff0c;即按时间顺序排列的数据。…

插入排序-C语言版本

前言 插入排序是很重要的排序&#xff0c;著名的希尔排序就是从插入排序演变过来的&#xff0c;所以我们需要并且很多时候有些面试也是会面试插入排序的&#xff0c;所以需要好好捋清楚插入排序的逻辑是什么 插入排序gif 插入排序单趟实现 1&#xff0c;插入排序我们需要假设最…

【高端精品】最新手机版微信小程序(拼多多+京东)全自动操作项目

现代互联网经济的发展带来了新型的盈利方式&#xff0c;通过微信小程序的拼多多和京东进行商品自动巡视&#xff0c;为商家带来增的流量&#xff0c;同时为使用者带来利润。这种盈利方式无需复杂操作&#xff0c;用户仅需启动相应程序&#xff0c;商品信息便会被系统自动收集。…

《现代通信原理与技术》码间串扰和​​​​​​​无码间串扰的眼图对比实验报告

实 验&#xff1a;码间串扰和无码间串扰的眼图对比实验报告 摘 要&#xff1a; 在数字通信系统中&#xff0c;码间串扰&#xff08;Inter-Symbol Interference, ISI&#xff09;是影响信号质量和系统性能的重要因素之一。本实验通过MATLAB软件生成并对比了受码间串扰影响和未…

记录一个flink跑kafka connector遇到的问题

【报错】 D:\Java\jdk1.8.0_231\bin\java.exe "-javaagent:D:\Program Files\JetBrains\IntelliJ IDEA 2022.2.3\lib\idea_rt.jar56647:D:\Program Files\JetBrains\IntelliJ IDEA 2022.2.3\bin" -Dfile.encodingUTF-8 -classpath D:\Java\jdk1.8.0_231\jre\lib\cha…

ubuntu搭建java开发环境IDEA版

一.安装 OpenJDK 更新包列表&#xff1a; sudo apt update安装 OpenJDK&#xff1a; 你可以选择安装不同版本的 OpenJDK&#xff0c;例如 11 或 17&#xff0c;这个是安装 OpenJDK 11 的命令&#xff1a; sudo apt install openjdk-11-jdk验证安装&#xff1a; 安装完成后…

C++ 59 之 纯虚函数和抽象类

#include <iostream> #include <string> using namespace std;class Cal { // 类中有纯虚函数&#xff0c;这个类也叫做抽象类&#xff0c;无法实现实例化 public:int m_a;int m_b;// 虚函数// virtual int getRes(){// return 0;// }// 纯虚函数 作用和虚函数…