我正在尝试将com.google.gson.JsonObject转换为case类对象。有时记录中的某些元素缺失,在这种情况下,我希望将它指定为案例类成员
object tmp {
case class person(name: String, age: Long)
def main(args: Array[String]): Unit = {
val parser = new JsonParser();
//PERSON 2
val record2 = parser.parse("""{"name":"xyz"}""").getAsJsonObject()
val record2_name = record2.get("name").getAsString.toLowerCase
val record2_age = if(record2.get("age") != null) record2.get("age") else None
val person2 = new person(record2_name,record2_age) //-> Type Mismatch, expected: Long, actual: Long
println(person2);
}
}
答案 0 :(得分:1)
您根本无法使用不同类型age: Long
的参数调用一种类型的参数Option[Long]
。
至少这是你的问题所暗示的。
您需要定义可能缺少的属性Option
。
e.g。在你的例子中
case class person(name: String, age: Option[Long])
然后当你提取json值时,你可以使用Option.apply
方法,如果参数为None
null
…
val record2_age = Option(record2.get("age")).map(_.getAsLong) // None if get("age) returns null
…
val person2 = new person(record2_name,record2_age) //There should be no more type mismatch now
答案 1 :(得分:0)
在您的情况下,public function handle($request, Closure $next, $guard = null)
{
if (Auth::guard($guard)->check()) {
return $request->user($guard)->is_admin
? redirect('/admin')
: redirect('/home');
}
return $next($request);
}
类型为record2_age
,类型为java JsonElement
,但由于您为其分配Object
,因此None
变为Any
您尝试分配给Long
类型的。
简短的回答是,
val person = new person(jsonObject.get("name").getAsString.toLowerCase,
Option(jsonObject.get("age")).map(_.getAsLong).getOrElse(0l))
这种方式如果jsonObject.get("age")
为空,Option(null)
会为您提供None
,或者如果有Option(28)
= Some(28)
如果空的话,您可能希望自己的年龄为0l
。如果您希望它为None
,则可以使用Option[Long]
。
1)更简单的方式
class GsonCaseClassSpecs extends FunSpec {
describe("case class conversion") {
it("converts gson with name/age to case class") {
case class person(name: String, age: Long)
val parser = new JsonParser()
//case 1
val jsonObject : JsonObject = parser.parse("""{"name":"xyz"}""").getAsJsonObject
val age = jsonObject.get("age") match {
case null => None
case value => Some(value.getAsLong)
}
val person1 = new person(jsonObject.get("name").getAsString.toLowerCase, age.getOrElse(0l))
assert(person1.name == "xyz")
assert(person1.age == 0)
//case 2
val jsonObject2 : JsonObject = parser.parse("""{"name":"xyz", "age" : 28}""").getAsJsonObject
val age2 : Option[Long] = jsonObject2.get("age") match {
case null => None
case value => Some(value.getAsLong)
}
val person2 = new person(jsonObject2.get("name").getAsString.toLowerCase, age2.getOrElse(0l))
assert(person2.name == "xyz")
assert(person2.age == 28)
}
}
}
2)如果您想让年龄为Option[Long]
。 Option[T]
可以有Some(x)
或None
。
class CaseClassFunSpecs extends FunSpec {
it("converts json to case class with empty age"){
case class person(name: String, age: Option[Long])
val parser = new JsonParser()
val json = parser.parse("""{"name":"xyz"}""").getAsJsonObject()
val personInstance = new person(json.get("name").getAsString.toLowerCase,
Option(json.get("age")).map(_.getAsLong))
assert(personInstance.name == "xyz")
assert(personInstance.age == None)
// NOTE
// do not do personInstance.age.get which would throw
// None.get
// java.util.NoSuchElementException: None.get
// at scala.None$.get(Option.scala:347)
// at scala.None$.get(Option.scala:345)
//rather use pattern match
personInstance.age match {
case Some(x) => println("value = " + x)
case None => throw new RuntimeException("Age can not be empty.")
}
}
it("converts json to case class with non-empty age"){
case class person(name: String, age: Option[Long])
val parser = new JsonParser()
val json = parser.parse("""{"name":"xyz", "age" : 28}""").getAsJsonObject()
val personInstance = new person(json.get("name").getAsString.toLowerCase,
Option(json.get("age")).map(_.getAsLong))
assert(personInstance.name == "xyz")
assert(personInstance.age == Some(28))
assert(personInstance.age.get == 28) //.get gives you the value
}
}