【问题标题】:Named parameter constructor in groovy and lombok @Valuegroovy 和 lombok @Value 中的命名参数构造函数
【发布时间】:2019-06-13 08:14:36
【问题描述】:

我有以下对象用来自 Lombok 的 @Value 注释:

@Value
public class Foo {
    private final boolean bar;
    private final boolean baz;
    private final boolean boo;
}

我尝试从 groovy 测试中实例化 Foo

new Foo(bar: true, baz: false, boo: true)

但我收到警告:

Constructor 'Foo' cannot be applied to '()'

在运行时出现以下错误:

Cannot set readonly property: bar for a class: Foo

有没有办法在 groovy 中使用命名构造函数来调用带有所有参数的构造函数,而不是调用空构造函数然后尝试设置字段?

【问题讨论】:

  • 您的Foo 课程是否有无参数控制器? Groovy 编译def f = new Foo(bar:baz) 的方式基本上是def f = new Foo(); f.bar = baz (groovy 中没有命名参数,它只是传递一个Map)
  • Groovy 内置了@Immutable 注解,你应该使用它来创建构造函数。

标签: java groovy lombok


【解决方案1】:
Constructor 'Foo' cannot be applied to '()'

这是因为你的类中的所有字段都是最终的,所以你必须在对象初始化期间初始化这些字段。

所以创建此类对象的唯一方法是使用全参数构造函数:

new Foo(true, false, true)

由于这种方式,Groovy 处理看起来像命名参数的东西(Groovy 支持命名参数 - 它传递一个 Map),这也会因类似的 Groovy 代码而失败。 Groovy 处理此处传递的映射的方式是将映射展开到 setter 调用中(并且没有,因为属性是最终的)。

@groovy.transform.TupleConstructor
class Foo {
    final boolean bar
    final boolean baz
    final boolean boo
}

new Foo(bar: true, baz: false, boo: true)

失败

Caught: groovy.lang.ReadOnlyPropertyException: Cannot set readonly property: bar for class: Foo
groovy.lang.ReadOnlyPropertyException: Cannot set readonly property: bar for class: Foo
        at x.run(x.groovy:8)

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2019-02-18
    • 1970-01-01
    • 2014-01-31
    • 1970-01-01
    • 2013-07-31
    • 1970-01-01
    • 1970-01-01
    • 2020-12-09
    相关资源
    最近更新 更多