Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

TypeScript type for reduce

Tags:

How would you declare a type for this properly?

interface MediaQueryProps {   [key: string]: number; }  const size: MediaQueryProps = {   small: 576,   medium: 768,   large: 992,   extra: 1200 };  export default Object.keys(size).reduce((acc, cur) => {   acc[cur] = `(min-width: ${size[cur]}px)`;    return acc; }, {}); 

acc[cur] is complaining because

Element implicitly has an 'any' type because expression of type 'string' can't be used to index type '{}'.   No index signature with a parameter of type 'string' was found on type '{}' 

Is there any way I can declare a type for this without using any?

like image 893
robert Avatar asked Aug 06 '19 15:08

robert


People also ask

How do you write reduce in TypeScript?

Use a generic to type the reduce() method in TypeScript, e.g. const result = arr. reduce<Record<string, string>>(myFunction, {}) . The generic is used to specify the type of the return and initial values of the reduce() method.

What is narrowing in TypeScript?

TypeScript follows possible paths of execution that our programs can take to analyze the most specific possible type of a value at a given position. It looks at these special checks (called type guards) and assignments, and the process of refining types to more specific types than declared is called narrowing.

What is reduce method in angular?

The reduce() method takes two arguments: a callback function and an optional initial value. If an initial value is provided, reduce() calls the "reducer" callback function on each element in the array, in order.

How do you reduce an array of objects?

The array reduce in JavaScript is a predefined method used to reduce an array to a single value by passing a callback function on each element of the array. It accepts a function executed on all the items of the specified array in the left-to-right sequence. The returned single value is stored in the accumulator.


2 Answers

If you want the accumulator value to be indexable by string, Record<string, string> should do the trick. You can pass this as the type argument to reduce

interface MediaQueryProps {   [key: string]: number; }  const size: MediaQueryProps = {   small: 576,   medium: 768,   large: 992,   extra: 1200 };  export default Object.keys(size).reduce<Record<string, string>>((acc, cur) => {   acc[cur] = `(min-width: ${size[cur]}px)`;   return acc; }, {}); 

Playground link

like image 148
Titian Cernicova-Dragomir Avatar answered Oct 11 '22 13:10

Titian Cernicova-Dragomir


You can do it like this using Record and keyof:

export default Object.keys(size).reduce((acc, cur) => {   acc[cur] = `(min-width: ${size[cur]}px)`;    return acc; }, {} as Record<keyof MediaQueryProps, string>); 
like image 26
Poul Kruijt Avatar answered Oct 11 '22 15:10

Poul Kruijt