Ooookay 这很长,但我希望它至少有所帮助!
这不是一个构造函数,因为它不是构造一个对象——它只是一个函数定义,当你用singleBattle()调用那个函数时,你需要传入列出的参数,把它们在括号中。
首先,是的,传递给函数的那些参数在函数块内变为本地vals - 它们是只读的。您可以对它们进行处理,并将结果分配给您在函数中声明的另一个 val 或 var。
但我假设你实际上想要做的是这样的:
- A 可以访问变量,例如
finalBossHealth
- A 将
finalBossHealth 传递给函数 B(作为 enemyhealth)
- B改变
enemyHealth的值
- A 看到
finalBossHealth 的变化,因为它是“同一个变量”
你不能这样做,因为你的参数是固定的vals。你基本上有两种选择:
在函数外部定义变量,A 和 B 都可以看到它们
只要函数和变量(字段)在同一个类中,它就会在同一个作用域中,并且可以直接改变它们。在这种情况下,传递该值没有任何意义,因为它可以直接读取和写入它们
var enemyHealth = 9999
public fun singleBattle() {
enemyHealth = enemyHealth - 100
}
实际上,您可能会有一个敌人列表或其他东西,并且您会传入一个索引,以便该函数可以查找并修改它。
返回一个更新的值供 A 使用
这是函数式方法 - 您传入某些数据,函数对其进行处理,然后将结果传递出去。理想情况下,如果您传入相同的数据,每次都会得到完全相同的结果 - 所以它只依赖于参数,而不是函数之外的任何状态(如类中的字段)。如果它在类之外没有任何副作用(比如更改类中的var),那么它被称为 pure 函数。
这些很容易推理,因为它们只做一件事 - 输入值,获得特定结果,很容易!
public fun singlebattle(enemyhealth : Int, enemyattack : Int , enemyname : String): Int {
// calculate whatever
return updatedHealth;
}
这个只返回一个Int,所以调用者会调用singleBattle,然后对结果做一些事情。 singleBattle 不需要知道任何关于外部状态的信息,它只需要一些值并对它们做一些有用的事情。
如果您需要返回多个值(例如可以减少攻击),您可以创建某种包含一堆值的数据结构:
data class Fighter(val health: Int, val attack: Int, val name: String)
public fun singlebattle(player: Fighter, enemy: Fighter): Fighter {
// calculate the player's state after the fight
return player.copy(health = newHealth)
// or just return Fighter(newHealth, player.attack, player.name)...
}
如果你想返回多个Fighter(这样你也有更新的敌人状态)你可能想使用另一个包含它们的对象,比如data class Battle(val fighter1: Fighter, fighter2: Fighter)
您可以利用将引用传递给函数的事实来组合这些(并失去纯函数的好处,但这样做可能更容易):
// I'm using vars here because we're gonna change them
data class Fighter(var health: Int, var attack: Int)
val player = Fighter(100, 999)
val monster1 = Fighter(9999, 5)
singleBattle(player, monster1)
fun singleBattle(fighter1: Fighter, fighter2: Fighter) {
// do the fight, update the values
fighter1.health = fighter1.health - fighter2.attack
// etc... you can also say fighter1 -= fighter2.attack as a shorthand
}
此函数不返回任何内容,因为它只是更改传入的Fighter 对象中的变量。调用将引用 传递给player 和monster1 对象,不是新副本,虽然您不能更改fighter1 的值(即它所指的Fighter 对象),但您可以在该对象内部四处寻找。并且所有可以看到同一个对象(有它的引用)的东西都会看到更新。所以在调用singleBattle(player, monster1) 之后,你会看到player1.health 等的新值,因为player1 指向内存中的同一个Fighter 对象,而fighter1 在函数搞乱它时所做的。