我正在尝试使某些生产Java适应Kotlin,但是我不得不把它降低一个档次,因为显然我什至都无法弄清基础知识。
Java:
public class Person {
private String name;
public Person(String name) { this.name = name; }
public String getName() { return name; }
public static void main(String[] args) {
Person p = new Person("me");
System.out.println(p.getName());
}
}
您将如何在Kotlin中做到这一点?也许只有这样:
// Person.kt
open class Person(var name: String)
$ kotlinc Person.kt && javap -p Person.class
Compiled from "Person.kt"
public class Person {
private java.lang.String name;
public final java.lang.String getName();
public final void setName(java.lang.String);
public Person(java.lang.String);
}
整洁,所以让所有自动生成的东西都可以使用:
open class Person(var name: String)
fun main(args: Array<String>) {
val p = Person("me")
println(p.getName())
}
$ kotlinc Person.kt
Person.kt:4:15: error: unresolved reference: getName
println(p.getName())
^
出什么问题了? p.name
可以工作,但是我猜那是因为它们都在同一文件中。哎呀,我什至无法测试这是真的:
// PersonDemo.kt in same dir as Person.kt
object PersonDemo {
fun main(args: Array<String>) {
val p = Person("me")
}
}
$ kotlinc PersonDemo.kt || (kotlinc Person.kt && kotlinc PersonDemo.kt)
PersonDemo.kt:3:17: error: unresolved reference: Person
var p = Person("me")
^
PersonDemo.kt:3:17: error: unresolved reference: Person
var p = Person("me")
^
也许可以导入?不,也不是。
清理classes和properties文档是没有用的,所以有人可以告诉我如何完成这些基本操作吗?
答案 0 :(得分:2)
只需在Person
类中编写以下代码并运行它即可。
// Person class in Kotlin
class Person(name:String) {
val name:String
// initializing name variable
init {
this.name = name
}
// main method converts to this in Kotlin
companion object {
@JvmStatic fun main(args:Array<String>) {
val p = Person("me")
println(p.name)
}
}
}
我们可以在这里删除初始化过程,因为我们可以直接从主构造函数访问name变量。因此,上面的Kotlin代码可以优化为:
class Person(val name: String) {
// main method converts to this in Kotlin
companion object {
@JvmStatic fun main(args:Array<String>) {
val p = Person("me")
println(p.name)
}
}
}
答案 1 :(得分:2)
您不能使用getName
,因为与Java相比,Kotlin在类属性上有一些不同的方法,在Java中,通常具有 getter 和 setter的私有属性用于访问的方法,在Kotlin中其标准具有属性。
有2种属性:
var
声明的变量使它们可变,并且可以更改其值,此属性具有与它们关联的两个方法set
和get
val
声明的那些使其不可变,因此它们的值无法更改,因为它们无法更改,因此它们仅具有get
方法。上面提到的get
和set
方法不需要指定。
因此,遵循Kotlin课:
open class Person(var name: String,val id: Int)
等效于以下Java类:
public class Person {
private String name;
private final int id;
public Person(String name, int id){
this.name = name;
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getId() {
return id;
}
}
请注意,id
是 val ,因此它只有 getter 。
每个属性在Kotlin中默认为public
,可以像在Java中一样在构造函数内部或类内部声明它们。当我们想要更改与该属性关联的get
和/或set
的默认行为时,使用最后提及的声明方法。
现在让其他人更好地解释这一点,让我举一个例子,让我们假设我们有上面使用过的类人,但是我们需要在每个名称前加上“名称:”。
在Java中,我们将通过以下方式重写上述 getter :
public String getName() {
return "Name: " + name;
}
要在Kotlin中获得相同的东西,我们需要编写如下内容:
open class Person(name: String,val id: Int){
var name: String = name
get() = "Name: $field"
}
请注意,我们没有在name
中使用get
,而是使用field
来引用我们的媒体资源,同样重要的是要注意我们没有写{{ 1}}或val
作为构造函数中的名称,这意味着它将只是常规参数。
关于属性的技巧很多,例如拥有var
但将var
设为私有,这样您就只能在该类内部更改值,后期初始化的属性等等。
作为答案的最后一部分,让我们看看如何使用 KOTLIN 编写的课程。
如果我们使用Kotlin代码中的该类:
set
在Java中使用相同的类:
val person = Person("KotlinPerson", 123)
person.name = "John"
val personName = person.name
val personId = person.id
最后,我也将添加相反的方法,您可以从上述代码中创建Person.java,并且Kotlin中的代码仍然可以正常工作,唯一的区别是使用Java代码时,您会得到{{1} },因为Java不保证某些值不为空。
答案 2 :(得分:0)
您将如何在Kotlin中做到这一点?
<exclusion>
<groupId>org.junit</groupId>
<artifactId>com.springsource.org.junit</artifactId>
</exclusion>