Ошибка объявления класса TypeScript с закрытой переменной - PullRequest
0 голосов
/ 07 мая 2018

Если у меня есть объявление класса TypeScript, подобное этому:

export class myClass {
  constructor(public aVariable: number) {}
  private aPrivateVariable: number;
}

и затем попытайтесь инициализировать его с помощью:

let someVar: myClass[] = [{
  aVariable: 3
}, {
  aVariable: 2
}];

Я получаю ошибку (по крайней мере, в VS Code), говорящую:

Свойство 'aPrivateVariable' отсутствует в типе '{aVariable: number; }».

Почему я не могу это сделать?

Спасибо.

Ответы [ 6 ]

0 голосов
/ 08 мая 2018
export class myClass {
   constructor(public aVariable: number) {}
   private aPrivateVariable: number;
}

Правильный способ был бы действительно инициализировать ваш класс следующим образом:

const someVar: myClass[] = [
    new myClass(3),
    new myClass(2),
]

Если вы не инициализируете свой класс, тогда вы хотите получить какие-либо методы из myClass, в результате вы получите объект, приведенный как myClass.

0 голосов
/ 07 мая 2018

Правильный способ инициализации этого класса -

export class myClass {
  constructor(public aVariable: number) {}
  private aPrivateVariable: number;
}

let someVar: myClass = new myClass(3);
0 голосов
/ 07 мая 2018

Определение объектов так, как вы это сделали ({ aVariable: 2}), не создает их экземпляры как myClass объекты. Это проблема, поскольку aPrivateVariable не создается, поскольку конструктор myClass никогда не вызывается, а добавляемый вами объект не соответствует содержимому myClass.

Как этот отрывок из справочника по машинописи о состояниях совместимости типов :

Закрытые и защищенные члены в классе влияют на их совместимость. Когда экземпляр класса проверяется на совместимость, если целевой тип содержит закрытый член, тогда тип источника также должен содержать закрытый член, происходящий из того же класса. Аналогично, то же самое относится к экземпляру с защищенным членом. Это позволяет классу быть совместимым по присваиванию со своим суперклассом, но не с классами из другой иерархии наследования, которые в остальном имеют одинаковую форму.

Один из способов справиться с этим - создать экземпляр каждого объекта, используя что-то вроде map()

const someVar: myClass[] = [2,3,1].map(num => myClass(num)) ;

Или, если вы уверены в форме объекта, вы можете использовать приведение типа:

let someVar: myClass[] = [] as myClass[]

Будьте осторожны с этим подходом, поскольку он не гарантирует, что то, что содержится в массиве, соответствует модели класса.

0 голосов
/ 07 мая 2018

Тип { aVariable: number; } не совместим с myClass

Как инструкция состояний,

Частные и защищенные члены в классе влияют на их совместимость. Когда экземпляр класса проверяется на совместимость, если целевой тип содержит закрытый член, тогда тип источника также должен содержать закрытый член, происходящий из того же класса. Аналогично, то же самое относится к экземпляру с защищенным членом. Это позволяет классу быть совместимым по присваиванию со своим суперклассом, но не с классами из другой иерархии наследования, которые в остальном имеют одинаковую форму.

Если myClass предполагается использовать в качестве интерфейса для назначения простых объектов, которые структурно совместимы с классом myClass, следует предоставить отдельный интерфейс:

interface IMyClass {
  aVariable: number;
}

export class myClass implements IMyClass {...}

let someVar: IMyClass[] = [{
  aVariable: 3
}];

и затем попытайтесь инициализировать его

Следует отметить, что приведенный выше код не инициализирует класс. Неясно, по каким причинам были назначены простые объекты вместо экземпляров класса, но если someVar должен содержать экземпляры myClass, ошибка типа указывает на проблему. Экземпляры должны быть явно созданы с помощью new:

let someVar: myClass[] = [new myClass(3)];
0 голосов
/ 07 мая 2018

Вы забыли объявить класс.Вы можете сделать это так

const someVar: myClass[] = [new myClass(3), new myClass(2)];
0 голосов
/ 07 мая 2018

Представьте, что у вашего класса также есть метод, который использует это поле:

 export class myClass {
  constructor(public aVariable: number) {}
  private aPrivateVariable: number;
  test(){  }
 }

Теперь, если вы сделаете следующее:

 const instance: myClass = {
    aVariable: 1,
    test() {
      alert.aPrivateVariable + 1);
    }
 };

 instance.test();

Это не удастся. Поэтому вам также необходимо добавить частные свойства.

 let someVar: myClass[] = [{
  aVariable: 3,
  aPrivateVariable: 2,
 }, {
  aVariable: 2,
  aPrivateVariable: 3
 }];
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...