最新消息:20210917 已从crifan.com换到crifan.org

【已解决】rcsjta项目编译出错:DisplayGeoloc.java使用了未经检查或不安全的操作

Java crifan 680浏览 0评论
折腾:
【未解决】Android Studio中gradle编译rcjsta项目多个使用或覆盖了已过时的API等报错
期间,gradle编译报错:
> Task :RI:compileDebugJavaWithJavac
注: 某些输入文件使用或覆盖了已过时的 API。
注: 有关详细信息, 请使用 -Xlint:deprecation 重新编译。
注: /Users/xxx/dev/xxx/RCS/rcsjta/RI/src/com/gsma/rcs/ri/messaging/geoloc/DisplayGeoloc.java使用了未经检查或不安全的操作。
注: 有关详细信息, 请使用 -Xlint:unchecked 重新编译。
去解决
但是找不到具体错误的位置。
那看看如何加上所说的
注: 有关详细信息, 请使用 -Xlint:unchecked 重新编译。
android studio 使用了未经检查或不安全的操作
.java使用了未经检查或不安全的操作。 注: 有关详细信息, 请使用 -Xlint:unchecked 重新编译。_weixin_41338006的博客-CSDN博客
去看看此处代码中是否有ArrayList类似写法
没有。
使用了未经检查或不安全的操作_A Flying Bird-CSDN博客
对于集合类,需要指定其类型。
后来有点看懂了:
代码右边有黄色标记
就表示:
警告类别的东西
最好去修改
而上面的:
mMapContactGeoloc = (HashMap<String, Geoloc>) getIntent()
        .getSerializableExtra(EXTRA_GEOLOC);
就是有警告
鼠标移动上去,看到提示:
Unchecked cast: 'java.io.Serializable' to 'java.util.HashMap<java.lang.String,com.gsma.services.rcs.Geoloc>' 
Try to generify 
More actions
点击More actions试试
算了。
还是去搜搜:
Try to generify
是啥意思
try to generify intellij
Generify refactoring – Help | IntelliJ IDEA
Generify dialog – Help | IntelliJ IDEA
Generify重构_w3cschool
Generify 重构前:
public void method() {
    List list = new LinkedList();
    list.add("string");
}
Generify 重构后:
public void method() {
    List<String> list = new LinkedList<String>();
    list.add("string");
}
很明显就是之前的:
对于集合类,需要指定其类型。
即:
IntelliJ IDEA 尝试生成代码,从 Java 的角度来看,这是尽可能正确的。换句话说,每个上下文都引入了一些类型限制,重构会产生最好的类型,这与现有的上下文不矛盾。
不过:
【已解决】Android Studio中gradle编译的项目如何加参数:-Xlint:unchecked
确认就是此处:
/Users/xxx/dev/xxx/RCS/rcsjta/RI/src/com/gsma/rcs/ri/messaging/geoloc/DisplayGeoloc.java:91: 警告: [unchecked] 未经检查的转换
                .getSerializableExtra(EXTRA_GEOLOC);
                                     ^
  需要: HashMap<String,Geoloc>
  找到:    Serializable
然后再去根据generify去试试:
点击 Preview
点击Do Refactor
好像没有任何变化。。。
然后就不太清楚,应该如何修改代码了。
Android Studio(JAVA) 编译警告:使用了未经检查或不安全的操作 – 默默的点滴
对于此处代码:
mMapContactGeoloc = (HashMap<String, Geoloc>) getIntent()
        .getSerializableExtra(EXTRA_GEOLOC);
去找找代码逻辑中的EXTRA_GEOLOC
src/com/gsma/rcs/ri/messaging/geoloc/DisplayGeoloc.java
public final static String EXTRA_GEOLOC = "geoloc";
就只是字符串而已
然后再去看看
getSerializableExtra
看起来,Android库中有对应实现。
另外从其他地方看起来是:
src/com/gsma/rcs/ri/messaging/geoloc/EditGeoloc.java
private OnClickListener btnValidateListener = new OnClickListener() {
    public void onClick(View v) {
。。。
Geoloc geoloc = new Geoloc(mLocationEdit.getText().toString(), Double.parseDouble(lat),
        Double.parseDouble(lon), expiration, Float.parseFloat(acc));
Intent in = new Intent();
in.putExtra(EXTRA_GEOLOC, (Parcelable) geoloc);
-》看起来是,至少别处有多个具体的实现
把EXTRA_GEOLOC和对应的Geoloc类的实例放到extra参数中
供其他地方调用
所以,上述,强制转换:
(HashMap<String, Geoloc>) 
逻辑上倒也没问题。
但是只是此处警告语法有问题
所以转去找找是否有其他更合法的写法
搜:
android getSerializableExtra
就看到提示有:
android getserializableextra cast
java – intent getSerializableExtra ClassCastException – Stack Overflow
android.content.Intent.getSerializableExtra java code examples | Codota
java – Class Cast Exception when passing array of Serializables from one activity to another – Stack Overflow
Android: onRecieve’s intent getSerializableExtra(String key) returns null – Stack Overflow
另外试了试:
Move initializer to constructor
结果这段代码,被移动到类的最开始了:
也不是我们希望的
且依旧被提示语法有问题
再试试勾选:
Generify Objects
结果:啥都没变。
没有生成要的,语法更好的代码。
尝试自己改改试试
android/content/Intent.java
/**
 * Retrieve extended data from the intent.
 *
 * @param name The name of the desired item.
 *
 * @return the value of an item that previously added with putExtra()
 * or null if no Serializable value was found.
 *
 * @see #putExtra(String, Serializable)
 */
public Serializable getSerializableExtra(String name) {
    return mExtras == null ? null : mExtras.getSerializable(name);
}
看到返回类型是:
String, Serializable
然后再去试试
import java.io.Serializable;

HashMap<String, Serializable> para_geoloc = getIntent().getSerializableExtra(EXTRA_GEOLOC);
mMapContactGeoloc = (HashMap<String, Geoloc>)para_geoloc;
结果语法错误:
去转换试试
HashMap<String, Serializable> para_geoloc = (HashMap<String, Serializable>) getIntent().getSerializableExtra(EXTRA_GEOLOC);
提示是:
和之前一样的
unchecked cast
那想到:
如何实现 checked cast?
android – How to solve Kotlin typecast issue? – Stack Overflow
android how do checked cast of intent
Intent to Join  |  Cast  |  Google Developers
android – Start cast session for a cast device – Stack Overflow
java – Application cannot be cast to android.app.Activity while checking permission – Stack Overflow
java – how to cast intent’s extra object[] to MyClas[] – Stack Overflow
classcastexception – class cast exception at android Broadcast receiver – Stack Overflow
Parcelable 与 Serializable – 简书
好像意思是:换Serializable为Parcelable 就可以 消除警告了?
此处没法转换,因为Serializable是内置的实现
不过试试getParcelableArrayListExtra能否用
不过搜:
EXTRA_GEOLOC
也才注意到,别处也有一些Parcelable相关的:
getParcelableExtra
src/com/gsma/rcs/ri/messaging/geoloc/EditGeoloc.java
@Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
    if (resultCode != RESULT_OK) {
        return;
    }
    switch (requestCode) {
        case REQUEST_CODE_SELECT_GEOLOC:
            Geoloc geoloc = data.getParcelableExtra(EXTRA_GEOLOC);
src/com/gsma/rcs/ri/sharing/geoloc/InitiateGeolocSharing.java
public void onActivityResult(int requestCode, int resultCode, Intent data) {
。。。
            /* Get selected geoloc */
            mGeoloc = data.getParcelableExtra(EditGeoloc.EXTRA_GEOLOC);
不过另外才明白了,此处的是DisplayGeoloc.java
要在同一个文件内找对应的 put的地方:
src/com/gsma/rcs/ri/messaging/geoloc/DisplayGeoloc.java
public static void showContactOnMap(Context ctx, ContactId contact, Geoloc geoloc) {
    HashMap<String, Geoloc> mapContactGeoloc = new HashMap<>();
    String displayName = RcsContactUtil.getInstance(ctx).getDisplayName(contact);
    mapContactGeoloc.put(displayName, geoloc);
    Intent intent = new Intent(ctx, DisplayGeoloc.class);
    intent.putExtra(DisplayGeoloc.EXTRA_GEOLOC, mapContactGeoloc);
    ctx.startActivity(intent);
}
和:
public static void showContactsOnMap(Context ctx, Set<ContactId> contacts) {
    HashMap<String, Geoloc> mapContactGeoloc = new HashMap<>();
    RcsContactUtil rcsContactUtil = RcsContactUtil.getInstance(ctx);
    for (ContactId contact : contacts) {
        Geoloc geoloc = getLastGeoloc(ctx, contact);
        if (geoloc != null) {
            mapContactGeoloc.put(rcsContactUtil.getDisplayName(contact), geoloc);
        }
    }
    Geoloc myGeoloc = getMyLastGeoloc(ctx);
    if (myGeoloc != null) {
        mapContactGeoloc.put(ctx.getString(R.string.label_me), myGeoloc);
    }
    if (mapContactGeoloc.isEmpty()) {
        Utils.displayLongToast(ctx, ctx.getString(R.string.label_geoloc_not_found));
        return;
    }
    Intent intent = new Intent(ctx, DisplayGeoloc.class);
    intent.putExtra(DisplayGeoloc.EXTRA_GEOLOC, mapContactGeoloc);
    ctx.startActivity(intent);
}
改为:
mMapContactGeoloc = (HashMap<String, Geoloc>) getIntent().getParcelableExtra(EXTRA_GEOLOC);
然后提示变了:
Unchecked cast: 'android.os.Parcelable' to 'java.util.HashMap<java.lang.String,com.gsma.services.rcs.Geoloc>' 

Casting 'getIntent().getParcelableExtra(...)' to 'HashMap<String, Geoloc>' is redundant 
好像是多余的,那就去掉看看:
mMapContactGeoloc = getIntent().getParcelableExtra(EXTRA_GEOLOC);
是没警告了。
但是参考的帖子
Parcelable 与 Serializable – 简书
人家改为Parcelable的前提是:对应内部实现PictureInfo的implements从Serializable改为了Parcelable
此处,需要去搞清楚,能否这么
直接改getSerializableExtra为getParcelableExtra
会不会导致其他异常?

getSerializableExtra  getParcelableExtra
Android Intent对象使用和Activity间数据的传递 – Livingstone – 博客园
果然是:
先要用:
Bundle.putParcelable(Key,Obj)
之后,后续才能用对应的:
getParcelableExtra
否则应该只能是:
Bundle.putSerializable(Key,Obj)
然后后续用:
getSerializableExtra
而此处的值是:
HashMap<String, Geoloc>
不知道是否支持?
难道是内部的HashMap 内置已至支持Parcelable?
Intent  |  Android 开发者  |  Android Developers
public class Intent 
extends Object implements Parcelable, Cloneable
不过本身Intent是,即实现了Parcelable,又实现了Cloneable
Retrieve extended data from the intent.
<T extends Parcelable>ArrayList<T>
Retrieve extended data from the intent.
<T extends Parcelable> T
Retrieve extended data from the intent.
https://developer.android.com/reference/android/content/Intent#getParcelableExtra(java.lang.String)
getParcelableExtra
Added in API level 1
public T getParcelableExtra (String name)
Retrieve extended data from the intent.
Parameters
name
String: The name of the desired item.
Returns
T
the value of an item previously added with putExtra(), or null if no Parcelable value was found.
See also:
putExtra(String, Parcelable)
返回之前通过 putExtra添加的值
那么对应着之前的:
intent.putExtra(DisplayGeoloc.EXTRA_GEOLOC, mapContactGeoloc);
或:
intent.putExtra(DisplayGeoloc.EXTRA_GEOLOC, mapContactGeoloc);
如果是这样的话,倒是上述代码,也没问题,可以这么改。
Serializable vs Parcelable in Android
也是类似的说法,对应的用于演示的类CustomClass,分别要实现Serializable或Parcelable
然后分别用:getSerializableExtra 或 getParcelableExtra
此处突然有点点明白,或许上述的:
HashMap<String, Geoloc>
其中整个作为整体,要支持Parcelable 就可以这么写
那么String自带支持
那么去看看:此处的Geoloc
src/main/java/com/gsma/services/rcs/Geoloc.java
public class Geoloc implements Parcelable, Serializable {
好了,即支持Serializable,也支持我们希望的Parcelable
所以就是可以这么写:
mMapContactGeoloc = getIntent().getParcelableExtra(EXTRA_GEOLOC);
估计是没问题的。
然后后续去编译和运行,希望此处代码不会报错,可以正常传递值过来。
待后续验证。
编译没问题。

【总结】
对于最初代码:
mMapContactGeoloc = (HashMap<String, Geoloc>) getIntent()
        .getSerializableExtra(EXTRA_GEOLOC);
编译报错:
注: 某些输入文件使用或覆盖了已过时的 API。
注: 有关详细信息, 请使用 -Xlint:deprecation 重新编译。
而去加了参数:
build.gradle
allprojects {
...

    gradle.projectsEvaluated {
        tasks.withType(JavaCompile) {
            options.compilerArgs << "-Xlint:unchecked"
        }
    }
}
后,可以确定就是上面代码报错。
且Android Studio中也能看到,该段代码背景土黄色,表示有问题。
鼠标移动上去提示:
Unchecked cast: 'java.io.Serializable' to 'java.util.HashMap<java.lang.String,com.gsma.services.rcs.Geoloc>'
根据提示:
Try to generify
Refactor
结果并没有重构。
通过研究代码,发现是:
此处getSerializableExtra所返回的值的类型,的确是,此处要强制cast转换的:
HashMap<String, Geoloc>
且:类Geoloc的源码是:
public class Geoloc implements Parcelable, Serializable {
即:不仅实现了Serializable,还实现了Parcelable
所以,为了消除代码警告,可以去改为Parcelable的写法:
mMapContactGeoloc = getIntent().getParcelableExtra(EXTRA_GEOLOC);
即可消除警告。
注:
关于Serializable和Parcelable的区别,和为何把Serializable换成Parcelable,是因为:
【整理】Android中的数据传递和序列化:Serializable和Parcelable
关于接口getParcelableExtra,可以参考:
Intent  |  Android 开发者  |  Android Developers
public T getParcelableExtra (String name)
https://developer.android.com/reference/android/content/Intent#getParcelableExtra(java.lang.String)

转载请注明:在路上 » 【已解决】rcsjta项目编译出错:DisplayGeoloc.java使用了未经检查或不安全的操作

发表我的评论
取消评论

表情

Hi,您需要填写昵称和邮箱!

  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址
92 queries in 0.176 seconds, using 23.37MB memory