Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/399.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 为什么可以';我是否对接收参数化参数的方法使用通配符?_Java_Generics_Wildcard_Parameterized - Fatal编程技术网

Java 为什么可以';我是否对接收参数化参数的方法使用通配符?

Java 为什么可以';我是否对接收参数化参数的方法使用通配符?,java,generics,wildcard,parameterized,Java,Generics,Wildcard,Parameterized,例如,我使用一种方法Measure.doubleValue(Unit),它返回测量值的double值,以指定的单位表示。如果我将单元变量传递给它,我会得到(对我来说)仍然非常神秘的错误消息: 方法 双值(单位)英寸 可测量的类型 不适用于参数 (单位) 如果有人能解释一下这是什么意思(或任何其他数字),以及是否有一种优雅的方法来摆脱这个问题,我将不胜感激。到目前为止,我删除了并设置了调用方法@SuppressWarnings(“unchecked”)(因此我传递了一个unchecked单元而不是

例如,我使用一种方法
Measure.doubleValue(Unit)
,它返回测量值的
double
值,以指定的
单位表示。如果我将
单元
变量传递给它,我会得到(对我来说)仍然非常神秘的错误消息:

方法
双值(单位)英寸
可测量的类型
不适用于参数
(单位)

如果有人能解释一下这是什么意思(或任何其他数字),以及是否有一种优雅的方法来摆脱这个问题,我将不胜感激。到目前为止,我删除了
并设置了调用方法
@SuppressWarnings(“unchecked”)
(因此我传递了一个unchecked
单元而不是
单元),并且一切都按预期工作,但我只是对此感到好奇,我觉得抑制警告不是一个好的做法(这不是有点像空的接球台吗?)

谢谢

编辑:添加一些代码。

(很抱歉,这很长,但它详细解释了我所坚持的内容。)

我正在使用(最近的)

所以…如果我写这个(非常愚蠢的例子):

它工作并打印“0.0030 km”。但我收到警告“测量是原始类型。对通用类型测量的引用应在“第一次
测量
发生和警告”类型安全:方法doubleValue(单位)属于原始类型可测量。对通用类型可测量的引用应参数化”超过
测量.doubleValue(单位为(“km”)的值)

看到这些警告,我想我可以这样调整(仅第一行):

这一行没有警告或错误;太棒了。但是,在第二行:

measure = Measure.valueOf(measure.doubleValue(Unit.valueOf("km")), Unit.valueOf("km"));
我为
doubleValue
“可测量类型中的方法doubleValue(Unit)不适用于参数(Unit)”。它建议将
Unit.valueOf(“km”)
转换为
(Unit)
。很好。现在我在完全相同的位置获得错误消息:“方法doubleValue(Unit)”在类型中,可测量的不适用于参数(单位)”。请注意,数字已更改,因此这不是完全相同的参数,而是一个类似的原因。然后,它执行完全相同的建议,这导致代码中没有任何更改,因为它已经完成


这就是困扰我的原因。让它工作的唯一方法似乎是
@SuppressWarnings
或者忽略它们。这不是很奇怪吗?

Java泛型中的通配符表示“未知类型”。在这里,您定义了
doubleValue()
方法接受一个
单元,其中
something1
不是由该方法指定的。然后,对于一些未知的
something2
,您传递一个调用者知道为
Unit
的值。编译器错误消息意味着没有任何东西可以保证
something1
something2
指定相同的内容

试试这个:

<T> double doubleValue(Unit<T> unit)
{
    ...
}
double doubleValue(单位)
{
...
}

这意味着
doubleValue()
不关心
T
是什么。

我无法重现您的问题,即以下编译很好(至少在eclipse中):

静态双精度值(单位){
返回0;
}
静态空隙bla(单位u){
双值(u);
}
公共静态void main(字符串[]args){
双值(新单位());
}

度量值类看起来像这样吗

class Measure<T> {

  double doubleValue(Unit<T> unit) {
    ...
  }

}
查看
测量
类文档中的示例。它们将提供一些额外的深度。

以扩展其他(优秀)答案,但更具体一点JSR-275(我目前正在将其用于一个项目)

这一点很有趣

修复建议:@SuppressWarnings,我更愿意避免它(我想是因为偏执的原因)

你的偏执是对的,但是想想看:你告诉
Measure
类解析任意
字符串,并返回任何类型的
Measure
。显然,在这种情况下,你可能会得到一个
Measure
(你可能会超过“3公斤”)因此,库剩下的唯一选项是返回
Measure
。如果需要
Measure
,则必须以某种方式将其强制为一个,这不可能在编译时保证安全

在这种情况下,我认为@SuppressWarnings是完全可以接受的,假设您知道字符串的长度始终是有效的。否则,您将不可避免的
ClassCastException
延迟到以后,这是非常糟糕的

更好的是(万岁!)JSR-275确实为您提供了一种解决方法,它将错误处理推到了“正确”的位置(在获取
度量值时,而不是在使用后的某个时间点)。试试看

Measure=Measure.valueOf(“3m”).aType(长度等级);
asType
返回
Measure
的适当通用版本,或者如果解析单元的维度不是长度,则异常失败——这几乎肯定是您想要的,对吗


我想这就解决了你的问题。

你有什么实际的代码可以看吗?泛型是非常“细节中的魔鬼”的东西.我同意Chris的观点。你可以用
单位
代替
单位
来解决你的问题,但是如果没有代码就很难说了。很抱歉耽搁了,不能再快了。我断章取义地写了一个示例代码,因为我认为现实生活中与此混合的一百行代码是不相关的。额外的代码有帮助。你绝对不应该压制警告;JSR-275已经竭尽全力利用泛型。我用一个解决方案更新了我的答案。我不能100%确定这些类是如何定义的。这个库的一个问题是,我们有最新的代码,
measure = Measure.valueOf(measure.doubleValue(Unit.valueOf("km")), Unit.valueOf("km"));
<T> double doubleValue(Unit<T> unit)
{
    ...
}
static double doubleValue(Unit<?> unit) {
    return 0;
}

static void bla(Unit<?> u) {
    doubleValue(u);
}

public static void main(String[] args) {
    doubleValue(new Unit<String>());
}
class Measure<T> {

  double doubleValue(Unit<T> unit) {
    ...
  }

}
Measure<?> unknownMeasure = valueOf("3 m");
Unit<?> unknownUnit = Unit.valueOf("km");
Measure<Length> length = unknownMeasure.asType(Length.class);
Unit<Length> kilometer = unknownUnit.asType(Length.class);
length.doubleValue(kilometer);
Measure<Length> = Measure.valueOf("3 m").asType(Length.class);