0

What I want is to make a JSON that looks like this.

{
    "filelist": [
        {
            "filename": "file1.txt",
            "oof": 0
        },
        {
            "filename": "file2.txt",
            "oof": 0
        },
        {
            "filename": "file3.txt",
            "oof": 0
        }
    ]
    
}

What I did was:

for line in listoflines:
    mysmalldict ["filename"] = line.strip("\n")
    mysmalldict ["oof"] = 0
    dictcollector.append(mysmalldict)

mybigdict[filelist"] = dictcollector
print(json.dumps(mybigdict))

Unfortunately, What I got was:

{
    "filelist": [
        {
            "filename": "file3.txt",
            "oof": 0
        },
        {
            "filename": "file3.txt",
            "oof": 0
        },
        {
            "filename": "file3.txt",
            "oof": 0
        }
    ]
    
}

Everything was overwritten by the last data.

After a couple of searches, I learned that Python dictionaries will overwrite data of the same keys. Some examples I found like this one doesn't fit my need as I need a duplicate key pair and not multiple values on one key.

I also found this one that is close but when I put the FakeDict on my dictcollector, it gives a different structure.

{
    "filelist": [
        '{
            "filename": "file3.txt",
            "oof": 0
        }',
        '{
            "filename": "file3.txt",
            "oof": 0
        }',
        '{
            "filename": "file3.txt",
            "oof": 0
        }'
    ]
    
}

Is there a way to do this in Python? Or did I miss something?

3
  • Thing is that dicts are passed by reference and whenever you change something in your dict it will be changed wherever you already passed it by reference. To solve it, you can append new dict in every iteration of for loop, like this: dictcollector.append({"filename": line ...}). Commented Mar 20, 2024 at 7:04
  • dictcollector.append(mysmalldict) This is your problem. You are not appending a copy of the dictionary as it exists in that moment -- you are appending the actual live dictionary object. (If it helps, you can think of this as a reference to the dictionary.) So when you update the dict with a new "filename" key in the next loop, you're also updating all the dicts that you previously appended to the list, because they are all the same object. Commented Mar 21, 2024 at 1:47
  • @MilosStojanovic so, this terminology is commonly used incorrectly, but nothing in Python is ever pass by reference, and the evaluation strategy doesn't depend on the type of object involved (there is only one evaluation strategy that is neither call by reference nor call by value) Commented Mar 21, 2024 at 15:47

2 Answers 2

1

You have to create a new dictionary on every iteration:

for line in listoflines:
    mysmalldict = {} # add this
    mysmalldict["filename"] = line.strip("\n")
    mysmalldict["oof"] = 0
    dictcollector.append(mysmalldict)

mybigdict["filelist"] = dictcollector
print(json.dumps(mybigdict))

In your example, you have created mysmalldict outside the loop and assigned it 3 times to dictcollector.

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

Comments

0

Instead of appending the dict, just append it as a whole.

Instead of

dictcollector.append(mysmalldict)

use

dictcollector.append({"key":"pair","key":"pair"})

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.