Access Object In Typescript/javascript
Solution 1:
Look at @Owl 's answer, it fixes the other problems in your code too.
In your loop the variable key
is not defined. You'd have to write it like this:
for (const key inthis.colorValues) {
...
}
Although I wouldn't use a for-in loop, since objects have their own prototype properties, which you would also receive in a for-in loop. A better solution would be this:
for (const key ofObject.keys(this.colorValues) {
...
}
But since you don't need the keys and just use them to retreive the values in the colorValues object, you could also use this:
for (const color ofObject.values(this.colorValues) {
...
}
Solution 2:
The cannot find name key
error is answered by @MrCodingB
A nicer way to write this:
classResistorColor {
privatecolors: string[]
public colorValues = {
black: 0,
brown: 1,
red: 2,
orange: 3,
yellow: 4,
green: 5,
blue: 6,
violet: 7,
grey: 8,
white: 9
}
constructor(colors: string[]) {
const colorValues = Object.keys(this.colorValues);
// colorValues is ["black", "brown", "red", ...]const isValid = colors.every(c => colorValues.includes(c));
// `every` is used to tests whether all elements in the array pass the test implemented by the provided function, // in this case, we check whether each value exists in `colorValues`if (isValid) {
this.colors = colors
} else {
thrownewError("Invalid Color(s)");
}
}
}
const resistorColor = newResistorColor(["black", "brown"]); // correctconsole.log("resistorColor has correct color");
const resistorColor2 = newResistorColor(["black", "brown", "gold"]); // throws errorconsole.log("resistorColor2 has correct color");
It's also possible to print out the incorrect colors value by using .filter()
classResistorColor {
privatecolors: string[]
public colorValues = {
black: 0,
brown: 1,
red: 2,
orange: 3,
yellow: 4,
green: 5,
blue: 6,
violet: 7,
grey: 8,
white: 9
}
constructor(colors: string[]) {
const colorValues = Object.keys(this.colorValues);
const invalidColors = colors.filter(c => !colorValues.includes(c));
if (invalidColors.length === 0) {
this.colors = colors
} else {
thrownewError(`Invalid Color -> ${invalidColors.join(", ")}`);
}
}
}
const resistorColor = newResistorColor(["black", "brown"]); // correctconsole.log("resistorColor has correct color");
const resistorColor2 = newResistorColor(["black", "brown", "gold", "foo"]); // throws error "Invalid Color -> gold, foo"
Solution 3:
Some of the errors that you are trying to prevent at run-time can be avoided at compile-time with stricter types. You can create a type that only allows specific string literal color names and you can also enforce a minimum length on the colors
array using tuple types.
It looks like this.colorValues
might just be an enum
?
enumCOLOR_VALUES {
black = 0,
brown = 1,
red = 2,
orange = 3,
yellow = 4,
green = 5,
blue = 6,
violet = 7,
grey = 8,
white = 9
}
typeColorNames = keyof typeofCOLOR_VALUES;
classResistorColor {
// can have two or more colorsconstructor(private colors: [ColorNames, ColorNames, ...ColorNames[]]) {
}
}
Now you can only call the constructor with valid arguments.
const a = newResistorColor(["black", "blue"]); // okconst b = newResistorColor(["black", "blue", "red"]); // okconst c = newResistorColor(["black"]); // error: Source has 1 element(s) but target requires 2.const d = newResistorColor(["white", "cyan"]); // error: Type '"cyan"' is not assignable to type
If this.colorValues
is an instance variable I would create the initial value outside of the class so that we can use typeof
.
constinitialValues= {
black:0,
brown:1,
red:2,
orange:3,
yellow:4,
green:5,
blue:6,
violet:7,
grey:8,
white:9
}
typeColorNames=keyoftypeofinitialValues;classResistorColor {
publiccolorValues=initialValues;//canhavetwoormorecolorsconstructor(privatecolors: [ColorNames, ColorNames, ...ColorNames[]]) {
}
}
Post a Comment for "Access Object In Typescript/javascript"