2012-02-13 2 views
0

У меня есть Scala def, который принимает параметры из HTTP POST и анализирует данные. Я вытаскиваю объект «job» из базы данных (запрос был успешным, как было проверено в отладчике, и параметры такие же, как и должны быть), и я пытаюсь обновить этот объект задания новыми параметрами. Однако попытка присвоения значений оказывается бесполезной, поскольку объект задания сохраняет все исходные значения.Как правильно установить значение объекта в Scala?

Все объекты базы данных принадлежат Squeryl. Код ниже:

Редактировать: добавлен класс ниже и объект Job, чтобы контекст воспроизводить в этой игре! приложение

object Job { 
    def updateFromParams(params:Params) = { 
    val job = Job.get(params.get("job_id").toLong).get 

    val comments = params.get("comments") 
    val startTime = parseDateTime(params.get("start_time") + " " + params.get("date")) 
    val endTime = parseDateTime(params.get("end_time") + " " + params.get("date")) 
    val clientId = params.get("client_id").toLong 
      val client = Client.get(clientId).get 
    val name = params.get("job_name") 
    val startAddressType = params.get("start_address_type") 
    var startLocationId:Option[Long] = None 
    val (startAddress, startCity, startProvince) = startAddressType match { 
     case "client" => getClientAddress(clientId) 
     case "custom" => (params.get("start_custom_address"), 
       params.get("start_custom_city"), 
       params.get("start_custom_province")) 
     case id => { 
     startLocationId = Some(id.toLong) 
     getLocationAddress(startLocationId.get) 
     } 
    } 

    job.comments -> comments 
    job.startTime -> startTime 
    job.endTime -> endTime 
    job.clientId -> clientId 
    job.name -> name 
    job.startAddressType -> startAddressType 
    job.startAddress -> startAddress 
    job.startCity -> startCity 
    job.startProvince -> startProvince 


    Job.update(job) 
    } 
} 

Я озадачен, потому что если я пытаюсь job.name -> name ничего не происходит, и если я пытаюсь job.name = name тогда я получаю ошибку reassignment to val Scala. Я получаю ту же ошибку при попытке var name вместо val name.

Это, очевидно, проблема синтаксиса с моей стороны, каков правильный способ справиться с этим? Благодаря!

Дополнительная информация:, если это помогает, вот класс работы, используемый в нашей игре! Приложение:

class Job(
    val id: Long, 

    @Column("name") 
    val name: String, 

    @Column("end_time") 
    val endTime: Timestamp, 

    @Column("start_time") 
    val startTime: Timestamp, 

    @Column("client_id") 
    val clientId: Long, 

    @Column("start_address_type") 
    var startAddressType:String, 

    @Column("start_address") 
    var startAddress: String, 
    /* LOTS MORE LIKE THIS */ 
) extends KeyedEntity[Long] { 
} 
+0

'x -> y' создает Tuple' (x, y) '. Это не оператор присваивания. Каково определение «Работа»? – leedm777

+0

Когда вы говорите, что вы меняете на 'var name', вы имеете в виду в этом коде или в определении' Job'? –

+0

'Работа' - это класс и модель в игре! фреймворк. Я добавлю класс в вопрос выше. :) – crockpotveggies

ответ

3

job.name непреложное свойство, так что вы не можете изменить его значение с job.name = name. В определении класса Job вы можете видеть, что name объявлен val, что означает его неизменность и никогда не может быть изменена. Единственный способ «изменить» значения объекта job - это создать совершенно новый экземпляр и отказаться от старого. Это стандартная практика при работе с неизменяемыми объектами.

Изменение местного значения name от val до var не имеет значения, так как вы только читаете значение этой переменной.

+0

Интересно, спасибо за полное объяснение все! У меня возникли трудности с подключением класса к проблеме. Я изменил класс, и теперь он работает! – crockpotveggies

0

val неизменяемы, в жире весь класс Job неизменен (поскольку все поля).

Что можно сделать, так это создать класс корпуса JobW и немного сутенерства, чтобы разрешить использование copy. Это говорит:

class Job(val id:Long, val name:String) {} 

case class JobW(override val id:Long, override val name:String) extends Job(id, name){ 
    def ok:String = name + id 
} 

implicit def wrapJob(job:Job):JobW = JobW(job.id, job.name) 

val job:Job = new Job(2L, "blah") 

println(job.ok) 

println(job.copy(name="Blob")) 

Что я сделал, чтобы обернуть (spimplified для упражнения) Работа в случае класса-обертки, и определить неявное преобразование.

Используя это неявное преобразование (то, что называется сутенерством), у вас будет доступ к методу ok, а также к copy.

Метод copy является введенным в класс case, который принимает столько аргументов, сколько класс case, как поля, и создает новый экземпляр класса case.

Итак, теперь у вас есть возможность изменить только одно значение вашего класса, очень просто я имею в виду и извлекаю новый объект (поскольку функциональное программирование сводится к неизменности).