第七色在线视频,2021少妇久久久久久久久久,亚洲欧洲精品成人久久av18,亚洲国产精品特色大片观看完整版,孙宇晨将参加特朗普的晚宴

為了賬號(hào)安全,請(qǐng)及時(shí)綁定郵箱和手機(jī)立即綁定
已解決430363個(gè)問(wèn)題,去搜搜看,總會(huì)有你想問(wèn)的

帶有泛型的 Vavr 給出了不兼容的類(lèi)型

帶有泛型的 Vavr 給出了不兼容的類(lèi)型

人到中年有點(diǎn)甜 2021-12-10 10:22:01
任何人都可以解釋為什么這個(gè)代碼:interface Lol {  default Try<Seq<? extends Number>> lol() {    return Try.of(List::empty);  }}class LolImpl implements Lol {  @Override  public Try<Seq<? extends Number>> lol() {    return Try      .of(() -> List.of(1, 2, 3))      //.onFailure(Object::hashCode)      ;  }}如果我取消注釋onFailure語(yǔ)句,編譯失敗?不知道這里會(huì)發(fā)生什么。如何改進(jìn)它?
查看完整描述

3 回答

?
開(kāi)滿天機(jī)

TA貢獻(xiàn)1786條經(jīng)驗(yàn) 獲得超13個(gè)贊

您可以Try.of()使用返回的顯式泛型類(lèi)型進(jìn)行調(diào)用以滿足編譯器檢查。就像是:


Try.<Seq<? extends Number>of(() -> List.of(1,2,3))

Try.of()返回類(lèi)型Try<T>其中T是供應(yīng)商返回的類(lèi)型。并且因?yàn)長(zhǎng)ist.of(T t...)return List<T>,那么編譯器看到的最終類(lèi)型是Try<List<Integer>,這不是方法返回的類(lèi)型定義的。具有特定類(lèi)型的 Java 泛型是不變的,它們不支持協(xié)變或逆變替換,因此List<Integer> != List<Number>.


工作示例:


import io.vavr.collection.List;

import io.vavr.collection.Seq;

import io.vavr.control.Try;


interface Lol {

    default Try<Seq<? extends Number>> lol() {

        return Try.of(List::empty);

    }

}


class LolImpl implements Lol {

    @Override

    public Try<Seq<? extends Number>> lol() {

        return Try

                .<Seq<? extends Number>>of(() -> List.of(1, 2, 3))

                .onFailure(t -> System.out.println(t.getMessage()));


    }


    public static void main(String[] args) {

        System.out.println(new LolImpl().lol());

    }

}

輸出:


Success(List(1, 2, 3))

通用示例類(lèi)型推斷問(wèn)題

進(jìn)一步調(diào)查表明,這很可能是一個(gè)通用的編譯器問(wèn)題??纯聪旅娴钠胀?Java 示例:


import java.util.Arrays;

import java.util.List;

import java.util.function.Supplier;


interface Some<T> {

    static <T> Some<T> of(Supplier<T> supplier) {

        return new SomeImpl<>(supplier.get());

    }


    default Some<T> shout() {

        System.out.println(this);

        return this;

    }


    class SomeImpl<T> implements Some<T> {

        private final T value;


        public SomeImpl(T value) {

            this.value = value;

        }

    }


    static void main(String[] args) {

        final Some<List<CharSequence>> strings = Some.of(() -> Arrays.asList("a", "b", "c"));

    }

}

此代碼編譯沒(méi)有任何問(wèn)題,編譯器Arrays.asList()從左側(cè)的預(yù)期類(lèi)型推斷返回的類(lèi)型:

http://img1.sycdn.imooc.com//61b2b9ee0001731207770193.jpg

現(xiàn)在,如果我調(diào)用這個(gè)Some<T>.shout()方法,它什么都不做并返回Some<T>,編譯器不是從預(yù)期的變量類(lèi)型,而是從最后返回的類(lèi)型推斷類(lèi)型:


http://img1.sycdn.imooc.com//61b2b9f90001bac708410137.jpg

當(dāng)然Arrays.asList("a","b","c")returnsList<String>this is the typeshout()`方法推斷并返回:


http://img1.sycdn.imooc.com//61b2ba0500016cb108100209.jpg

指定顯式類(lèi)型Some<T>.of()可以解決問(wèn)題,如Try.of()示例所示:

http://img1.sycdn.imooc.com//61b2ba11000191d609550084.jpg

我正在搜索有關(guān)類(lèi)型推斷的 Oracle 文檔,并且有以下解釋?zhuān)?/p>

Java 編譯器利用目標(biāo)類(lèi)型來(lái)推斷泛型方法調(diào)用的類(lèi)型參數(shù)。表達(dá)式的目標(biāo)類(lèi)型是 Java 編譯器期望的數(shù)據(jù)類(lèi)型,具體取決于表達(dá)式出現(xiàn)的位置。

來(lái)源:https : //docs.oracle.com/javase/tutorial/java/generics/genTypeInference.html#target_types

在這種情況下,看起來(lái)“取決于表達(dá)式出現(xiàn)的位置”意味著從先前返回的確切類(lèi)型推斷類(lèi)型。這將解釋為什么跳過(guò)shout()方法使編譯器知道,我們期望Some<List<CharSequence>>并且當(dāng)我們添加shout()方法時(shí)它開(kāi)始返回Some<List<String>>,因?yàn)檫@是shout()方法從返回的Some.of()方法類(lèi)型中看到的。希望能幫助到你。


查看完整回答
反對(duì) 回復(fù) 2021-12-10
?
子衿沉夜

TA貢獻(xiàn)1828條經(jīng)驗(yàn) 獲得超3個(gè)贊

您的問(wèn)題的答案與 Java 的類(lèi)型推斷以及類(lèi)型方差(在我們的示例中為協(xié)方差)有關(guān)。它與 Vavr 沒(méi)有任何關(guān)系。


Try<List<Integer>>是 的子類(lèi)型Try<? extends Seq<? extends Number>>。

但Try<List<Integer>>不是 的子類(lèi)型Try<Seq<? extends Number>>。

將lol()方法的返回類(lèi)型更改為T(mén)ry<? extends Seq<? extends Number>>,所有都將編譯正常。


讓我們來(lái)詳細(xì)看看。


public Try<Seq<? extends Number>> lol() {  // line 1

    return Try.of(() -> List.of(1, 2, 3))  // line 2

        //.onFailure(Object::hashCode)     // line 3

    ;

}

該lol()方法確實(shí)返回一個(gè)類(lèi)型的值Try<Seq<? extends Number>>(參見(jiàn)第 1 行)。


第 2 行中的 return 語(yǔ)句返回一個(gè)Try使用工廠方法構(gòu)造的實(shí)例Try.of(...)。在 Vavr 0.9.x 中,它是這樣定義的:


static <T> Try<T> of(CheckedFunction0<? extends T> supplier) {

    // implementation omitted

}

編譯器推斷:


// type T = Seq<? extends Number>

Try.of(() -> List.of(1, 2, 3))

因?yàn)樗枰瑫r(shí)匹配方法的返回類(lèi)型lol()和CheckedFunction0工廠方法的簽名Try.of。


這編譯得很好,因?yàn)樵搒upplier函數(shù)返回一個(gè) type 值? extends T,即? extends Seq<? extends Number>,它與實(shí)際返回類(lèi)型兼容List<Integer>(參見(jiàn)上面的 TL;DR 部分)。


如果我們現(xiàn)在取消注釋.onFailure部分(第 3 行),那么T工廠方法的泛型類(lèi)型參數(shù)Try.of不再具有返回類(lèi)型的范圍lol()。編譯器推斷T為是,List<Integer>因?yàn)樗偸窃噲D找到適用的最具體的類(lèi)型。


.onFailure返回類(lèi)型的值,List<Integer>因?yàn)槿绻膶?shí)例返回完全相同的類(lèi)型。但Try<List<Integer>>不是Try<Seq<? extends Number>>(參見(jiàn)上面的 TL;DR 部分)的子類(lèi)型,因此代碼不再編譯。


使lol()方法在其返回類(lèi)型中協(xié)變將滿足編譯器:


// before: Try<Seq<? extends Number>>

Try<? extends Seq<? extends Number>> lol() { // line 1

    return Try.of(() -> List.of(1, 2, 3))    // line 2

        .onFailure(Object::hashCode);        // line 3

}

順便說(shuō)一句,在 Vavr 的整個(gè)類(lèi)型層次結(jié)構(gòu)中定義正確的泛型變量,尤其是對(duì)于集合,是創(chuàng)建 Vavr 時(shí)的難點(diǎn)之一。Java 的類(lèi)型系統(tǒng)并不完善,還有一些東西是我們不能用 Java 的泛型來(lái)表達(dá)的。另請(qǐng)參閱我的博客文章“未來(lái) Java 中的聲明站點(diǎn)差異”


免責(zé)聲明:我是 Vavr(以前稱為 Javaslang)的創(chuàng)建者


查看完整回答
反對(duì) 回復(fù) 2021-12-10
?
心有法竹

TA貢獻(xiàn)1866條經(jīng)驗(yàn) 獲得超5個(gè)贊

似乎 Java 編譯器無(wú)法為您推斷出正確的類(lèi)型,在這種情況下,您需要提供繼續(xù)操作所需的其他類(lèi)型信息,例如:


class LolImpl implements Lol {


    @Override

    public Try<Seq<? extends Number>> lol() {

        Try<Seq<? extends Number>> res = Try.of(() -> List.of(1, 2, 3));

        return res.onFailure(Object::hashCode);

    }

}


查看完整回答
反對(duì) 回復(fù) 2021-12-10
  • 3 回答
  • 0 關(guān)注
  • 270 瀏覽
慕課專(zhuān)欄
更多

添加回答

舉報(bào)

0/150
提交
取消
微信客服

購(gòu)課補(bǔ)貼
聯(lián)系客服咨詢優(yōu)惠詳情

幫助反饋 APP下載

慕課網(wǎng)APP
您的移動(dòng)學(xué)習(xí)伙伴

公眾號(hào)

掃描二維碼
關(guān)注慕課網(wǎng)微信公眾號(hào)