我不知道为什么,但如果实例变量文本是私有的,下面的课程不起作用,但是如果我省略私有,它就有效。
在第34节中调试测试; setField"我可以看到实例变量名称应为" text"但它变成了" com $ test $ SimpleTest $$ text"
package com.test
import org.testng.annotations.Test
import org.springframework.test.util.ReflectionTestUtils
class SimpleTest {
private var text = ""
@Test
def testValueOfX(): Unit = {
val simpleTest = new SimpleTest
ReflectionTestUtils.setField(simpleTest,"text", "abc")
println(
Option[String](null)
.map(v => v + " 123")
.getOrElse {
simpleTest.text + " 321"
})
}
}
我认为这个问题无论如何都是" getOrElse"因为如果我也遗漏了,那就行了。
答案 0 :(得分:2)
Scala编译器有权将您的私有字段编译成任何可用的java代码,因为它不会影响互操作性(如果您不做任何技巧)。 Spring setField
实际上做了这样的技巧,因为它使你的私有字段可访问(setAccessible(true)
里面)。公共字段总是在编译,以便为您提供适当的Java接口。
使用http://docs.scala-lang.org/overviews/reflection/environment-universes-mirrors.html处理Scala反射。 this article也可能会有所帮助。
Here解释了为什么scalac为私有字段使用其他名称。
P.S。删除.getOrElse(text)
使其有效的原因是因为您不在任何地方使用text
,而是在此段代码中。
答案 1 :(得分:0)
这个类只是为了显示问题,实际上它与真实类有很大的不同。所以我改变策略以通过@Autowired方法接收一个实例而不是@Autowired一个字段。
package com.test
import org.testng.annotations.Test
import org.springframework.test.util.ReflectionTestUtils
class SimpleTest {
// item 1
private var text = ""
@Test
def testValueOfX(): Unit = {
val simpleTest = new SimpleTest
ReflectionTestUtils.invokeSetterMethod(simpleTest, "text", "abc")
println(
Option[String](null)
.map(v => v + " 123")
.getOrElse {
simpleTest.text + " 321"
})
}
// item 2
def setText(text: String): Unit = {
this.text = text
}
}
我不是在这个样本中使用@Autowired,而是在我真正的课堂上。因此,如果您需要获取实例,请按照以下说明操作。
项目1 - >如果我加上@Autowired它不起作用,因为像 dk14 Scala编译器有权将你的私有字段编译成任何工作的java代码。因此,编译器在编译类
时会更改字段的名称第2项 - >我在setter方法中加入@Autowired,它可以工作。