1

I am trying to end up with a dictionary of list of dictionaries and I am having difficulty adding elements to it. What I have is a simple enough CSV, that looks like so in excel.

enter image description here

The above is parsed using papa.parse to be an array of dictionaries with the headers the keys of the dictionaries, but I need to format it in a specific way.

What I need to end up with is a dictionary whose first entry:

finalDict = {
    state: "CA",
    governor: {
        first_name: "Gavin",
        last_name: "Newsom"
    },
    cities: [{city1: "LA", population: "8M", mayor: "ABC"},
             {city2: "SF", population: "1M", mayor: "DEF"}]
}

It seemed like it should be simple enough and I wrote a function that takes a file and iterates through but am having difficulty with the "cities" key above:

function parseFile(csv) {
    let stateGovs = {
        state: "",
        governor: {
            first_name:"",
            last_name:""
        },
        cities:[]
    }

    // Note I can write more detail in my for loop upon request, but this is where the issue is
    csv.forEach((entry) => {
        // insert some more parsing logic, but I end up with a temp variable that looks like
        temp = {city1: "LA", population: "8M", mayor: "ABC"}
        // and I say
        stateGovs.cities.push(temp)    
    }
}

The way I have defined cities in my dict, intellisense tells me it is of type never[] and when I try to push anything to it (namely my temp dictionary), I get the warning:

"argument of type any[]/{} is not assignable to parameter of type 'never'"

and that is where I am stuck.

I have tried making my temp variable a list a dict, explicitly defining a type outside my function, but the crux of the issue is this and nothing seems to work as I do not know (enough) of what I am doing wrong here. Any help would be appreciated.

1 Answer 1

2

When you initialize an empty array, TypeScript infers it implicitly as any[] in simple situations (see ms/TS#18687), or as never[] type otherwise (like in your case for property stateGovs.cities: []).

Hence it considers that anything that you try pushing into that array is incorrect, since nothing is assignable to never.

In many cases we plan to populate the empty array later on. Simply tell TypeScript what the array is supposed to contain:

interface City {
    city1: string
    population: string
    mayor: string
}

const cities: City[] = []
const cities2: Array<City> = [] // Alternative syntax
const cities3 = [] as City[] // Type assertion

See also e.g. What is "not assignable to parameter of type never" error in TypeScript? or https://www.geeksforgeeks.org/how-to-avoid-inferring-empty-array-in-typescript/

In your case you could simply do:

const stateGovs2 = {
    state: "",
    governor: {
        first_name: "",
        last_name: ""
    },
    cities: [] as City[] // Type assertion
}

...and now TypeScript lets you push into the array objects that comply with the City interface:

stateGovs2.cities.push(temp) // Okay
//         ^? City[]

Playground Link

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.