gpt4 book ai didi

具有多个通用参数的 java lambda 表达式未编译

转载 作者:行者123 更新时间:2023-11-30 06:34:54 25 4
gpt4 key购买 nike

我正在编写 Excel 导入逻辑:

public class ExcelImporter {
//...ignore constructor and other methods ...
public <R> Builder<R> sheet(String sheetName, RowConsumer<R> rowConsumer) {
return new Builder<R>(sheetName, rowConsumer);
}
public class Builder<R> {
//...ignore other method
public <F> Builder header(String name, CellConsumer<R, F> cellConsumer) {
sheetReader.header(new DefaultHeader<>(name, cellConsumer));
return this;
}
public <F> Builder header(String name, Class<F> fieldType, CellConsumer<R, String> cellConsumer) {
return header(name,cellConsumer);
}
}
}

在我的测试代码中,我遇到了编译错误:

@Test
public void processSmallExcelWithConsumer() throws Exception {
try (InputStream is = getClass().getClassLoader().getResourceAsStream("工作簿1.xls")) {
ExcelImporter excelImporter = new ExcelImporter(is, "application/vnd.ms-excel")
.sheet("Sheet1", () -> new RowBean())
.header("姓名",String.class, (cell, row) -> row.setName(cell)) // no error
.header("性别",String.class, (cell, row) -> row.setSex(cell)) // "setSex" got error and `row` evaluate to `Object` ? why !?
.build();

setSex() 无法编译,并且 row 评估为 Object,我很困惑,它第一次运行得很好但下次又失败了?

这是CellConsumer:

@FunctionalInterface
public interface CellConsumer<R,F> {
void read(F cell,R row);
}

RowConsumer:

@FunctionalInterface
public interface RowConsumer<R> {
R newRow();
}

和错误:

[INFO] BUILD FAILURE
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 1.797 s
[INFO] Finished at: 2017-07-28T23:56:26+08:00
[INFO] Final Memory: 17M/166M
[INFO] ------------------------------------------------------------------------
[ERROR] Failed to execute goal org.apache.maven.plugins:maven-compiler-plugin:3.2:testCompile (default-testCompile) on project graceful-excel: Compilation failure
[ERROR] /home/terrason/workspace/maven/cnx/graceful-excel/src/test/java/cn/lenyar/excel/ExcelImporterTest.java:[81,66] 找不到符号
[ERROR] 符号: 方法 setSex(java.lang.Object)
[ERROR] 位置: 类型为java.lang.Object的变量 row
[ERROR] -> [Help 1]

请帮帮我!

最佳答案

问题是您没有在 header 方法中指定返回的构建器的通用类型:

public <F> Builder header(...)
//this returns Builder which is the same as Builder<?>
//All java can infer from Builder<?> is that the generic type is an Object.
//which makes row in the second call an Object

尝试返回Builder<R>在你的header方法:

public class ExcelImporter {
//...ignore constructor and other methods ...
public <R> Builder<R> sheet(String sheetName, RowConsumer<R> rowConsumer) {
return new Builder<R>(sheetName, rowConsumer);
}

private static class RowBean {
private String name;
private String sex;

public void setName(String name) {
this.name = name;
}

public void setSex(String sex) {
this.sex = sex;
}
}

public class Builder<R> {
public Builder(String sheetName, RowConsumer<R> rowConsumer) {

}

//...ignore other method
public <F> Builder<R> header(String name, CellConsumer<R, F> cellConsumer) {
return this;
}

public <F> Builder<R> header(String name, Class<F> fieldType, CellConsumer<R, String> cellConsumer) {
return header(name, cellConsumer);
}

public ExcelImporter build() {
return null;
}
}

@FunctionalInterface
public interface CellConsumer<R, F> {
void read(F cell, R row);
}

@FunctionalInterface
public interface RowConsumer<R> {
R newRow();
}

public static void main(String[] args) {
ExcelImporter excelImporter = new ExcelImporter()
.sheet("Sheet1", () -> new RowBean())
.header("姓名", String.class, (cell, row) -> row.setName(cell)) // no error
.header("性别", String.class, (cell, row) -> row.setSex(cell)) // no error!
.build();
}
}

关于具有多个通用参数的 java lambda 表达式未编译,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45377598/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com