Как добавить экземпляр структуры в хеш-таблицу? Я продолжаю возвращать цитируемый список - PullRequest
4 голосов
/ 03 июля 2019

Я пишу простой маленький roguelike для изучения ракетки. Я застрял на чем-то очень простом - создании фабрики игровых объектов с использованием хеш-таблицы. Типичный способ сделать это (как в clojure или других) - создать ключевое слово (например, «игрок») и добавить экземпляр объекта для игрового объекта такого типа, который я затем клонировал бы при необходимости.

Я явно упускаю что-то простое здесь. Извините за простой вопрос.

Я пробовал несколько версий создания списка хешей. Единственный способ заставить его работать, это просто поместить атрибуты в список хешей и вместо использования struct-copy использовать apply. Но это не очень хорошо работает, когда они являются вложенными структурами внутри базовой структуры.

;racket
#lang racket

(struct loc (x y) #:transparent)
(struct object (rep color loc) #:transparent)
(struct world (player running) #:transparent)

(define object-templates 
  #hash(["player" . (object "@" "green" (loc 0 0))]))

(define (make-object type) (struct-copy object (dict-ref object-templates type)))


; struct-copy: contract violation
;   expected: object?
;   given: '(object "@" "green" (loc 0 0))

Понятия не имею, почему я получаю это в виде цитируемого списка. Вместо экземпляра объекта. Я чувствую, что мне не хватает некоторого синтаксического сахара в (определите шаблоны объектов выше, но я не смог его найти.

1 Ответ

6 голосов
/ 03 июля 2019

Попробуйте:

(define object-templates 
  (hash "player" (object "@" "green" (loc 0 0))))

Проблема в том, что #hash(...) процитирует все внутри него.Используйте hash (или make-hash для изменяемого хэша, хотя формат аргумента отличается), если вы хотите разрешить оценку.

Это похоже на '(object) против (list object) или #(object) против(vector object) и т. Д.

...