Home > Blockchain >  python append to list in a for loop
python append to list in a for loop

Time:11-30

below you can see a piece of simplified code, but the problems I'm having are clearly visible. I have a dict filled with data. It's from a get rerquest. So I can't change the strucure. I want to add the output of the print(test(data,x)) in the list but the list contains other data. When I looked up this problem I saw that I had to use .copy()/list() but I can't find a way to get this to work.

New code(after somme possible improvements)

data = {"datasource": "InfluxDB", "gridPos": {"h": 4, "w": 3, "x": 3, "y": 14}, "id": 80, "targets": [{"measurement": "database"}, {"measurement": "database"}],"title": "Name"}
test_list = []

def test(data,database):
    data = data.copy()
    data['gridPos']['x']  = data['gridPos']['w']   1
    data['gridPos']['y']  = data['gridPos']['h']   1
    data['id']  = 1
    data['targets'][0]['measurement']  = str(database) 
    return data

for x in range(0,10):
    data = test(data,x)
    test_list.append(data.copy())

test_list
data = {"datasource": "InfluxDB", "gridPos": {"h": 4, "w": 3, "x": 3, "y": 14}, "id": 80, "targets": [{"measurement": "database"}, {"measurement": "database"}],"title": "Naam"}
test_list = []

def test(data,database):
    data['gridPos']['x']  = data['gridPos']['w']   1
    data['gridPos']['y']  = data['gridPos']['h']   1
    data['id']  = 1
    data['targets'][0]['measurement']  = str(database) 
    return data

for x in range(0,10):
    print(test(data,x))
    test_list.append(test(data,x).copy())

print(test_list)

print(test(data,x)) (in the foor loop)

{'datasource': 'InfluxDB', 'gridPos': {'h': 4, 'w': 3, 'x': 7, 'y': 19}, 'id': 81, 'targets': [{'measurement': 'database0'}, {'measurement': 'database'}], 'title': 'Name'}
{'datasource': 'InfluxDB', 'gridPos': {'h': 4, 'w': 3, 'x': 15, 'y': 29}, 'id': 83, 'targets': [{'measurement': 'database001'}, {'measurement': 'database'}], 'title': 'Name'}
{'datasource': 'InfluxDB', 'gridPos': {'h': 4, 'w': 3, 'x': 23, 'y': 39}, 'id': 85, 'targets': [{'measurement': 'database00112'}, {'measurement': 'database'}], 'title': 'Name'}
{'datasource': 'InfluxDB', 'gridPos': {'h': 4, 'w': 3, 'x': 31, 'y': 49}, 'id': 87, 'targets': [{'measurement': 'database0011223'}, {'measurement': 'database'}], 'title': 'Name'}
{'datasource': 'InfluxDB', 'gridPos': {'h': 4, 'w': 3, 'x': 39, 'y': 59}, 'id': 89, 'targets': [{'measurement': 'database001122334'}, {'measurement': 'database'}], 'title': 'Name'}
{'datasource': 'InfluxDB', 'gridPos': {'h': 4, 'w': 3, 'x': 47, 'y': 69}, 'id': 91, 'targets': [{'measurement': 'database00112233445'}, {'measurement': 'database'}], 'title': 'Name'}
{'datasource': 'InfluxDB', 'gridPos': {'h': 4, 'w': 3, 'x': 55, 'y': 79}, 'id': 93, 'targets': [{'measurement': 'database0011223344556'}, {'measurement': 'database'}], 'title': 'Name'}
{'datasource': 'InfluxDB', 'gridPos': {'h': 4, 'w': 3, 'x': 63, 'y': 89}, 'id': 95, 'targets': [{'measurement': 'database001122334455667'}, {'measurement': 'database'}], 'title': 'Name'}
{'datasource': 'InfluxDB', 'gridPos': {'h': 4, 'w': 3, 'x': 71, 'y': 99}, 'id': 97, 'targets': [{'measurement': 'database00112233445566778'}, {'measurement': 'database'}], 'title': 'Name'}
{'datasource': 'InfluxDB', 'gridPos': {'h': 4, 'w': 3, 'x': 79, 'y': 109}, 'id': 99, 'targets': [{'measurement': 'database0011223344556677889'}, {'measurement': 'database'}], 'title': 'Name'}

print(test_list)

[{'datasource': 'InfluxDB',
  'gridPos': {'h': 4, 'w': 3, 'x': 83, 'y': 114},
  'id': 82,
  'targets': [{'measurement': 'database00112233445566778899'},
   {'measurement': 'database'}],
  'title': 'Name'},
 {'datasource': 'InfluxDB',
  'gridPos': {'h': 4, 'w': 3, 'x': 83, 'y': 114},
  'id': 84,
  'targets': [{'measurement': 'database00112233445566778899'},
   {'measurement': 'database'}],
  'title': 'Name'},
 {'datasource': 'InfluxDB',
  'gridPos': {'h': 4, 'w': 3, 'x': 83, 'y': 114},
  'id': 86,
  'targets': [{'measurement': 'database00112233445566778899'},
   {'measurement': 'database'}],
  'title': 'Name'},
 {'datasource': 'InfluxDB',
  'gridPos': {'h': 4, 'w': 3, 'x': 83, 'y': 114},
  'id': 88,
  'targets': [{'measurement': 'database00112233445566778899'},
   {'measurement': 'database'}],
  'title': 'Name'},
 {'datasource': 'InfluxDB',
  'gridPos': {'h': 4, 'w': 3, 'x': 83, 'y': 114},
  'id': 90,
  'targets': [{'measurement': 'database00112233445566778899'},
   {'measurement': 'database'}],
  'title': 'Name'},
 {'datasource': 'InfluxDB',
  'gridPos': {'h': 4, 'w': 3, 'x': 83, 'y': 114},
  'id': 92,
  'targets': [{'measurement': 'database00112233445566778899'},
   {'measurement': 'database'}],
  'title': 'Name'},
 {'datasource': 'InfluxDB',
  'gridPos': {'h': 4, 'w': 3, 'x': 83, 'y': 114},
  'id': 94,
  'targets': [{'measurement': 'database00112233445566778899'},
   {'measurement': 'database'}],
  'title': 'Name'},
 {'datasource': 'InfluxDB',
  'gridPos': {'h': 4, 'w': 3, 'x': 83, 'y': 114},
  'id': 96,
  'targets': [{'measurement': 'database00112233445566778899'},
   {'measurement': 'database'}],
  'title': 'Name'},
 {'datasource': 'InfluxDB',
  'gridPos': {'h': 4, 'w': 3, 'x': 83, 'y': 114},
  'id': 98,
  'targets': [{'measurement': 'database00112233445566778899'},
   {'measurement': 'database'}],
  'title': 'Name'},
 {'datasource': 'InfluxDB',
  'gridPos': {'h': 4, 'w': 3, 'x': 83, 'y': 114},
  'id': 100,
  'targets': [{'measurement': 'database00112233445566778899'},
   {'measurement': 'database'}],
  'title': 'Name'}]

CodePudding user response:

Your test function transforms data , and you call it twice - once to print and once to append, so it transforms the dictionary twice in each iteration. In addition, copy only makes a shallow copy of the dictionary, but you need a deep copy because it contains nested dictionaries and lists.

To fix this, import copy and change this line

test_list.append(test(data,x).copy())

To

test_list.append(copy.deepcopy(data)) # data has already been transformed so no need to call `test` again

Or better, change the structure so that your function does not have side effects:

def test(data,database):
    data = copy.deepcopy(data)
    data['gridPos']['x']  = data['gridPos']['w']   1
    data['gridPos']['y']  = data['gridPos']['h']   1
    data['id']  = 1
    data['targets'][0]['measurement']  = str(database) 
    return data

for x in range(10):
    data = test(data,x)
    print(data)
    test_list.append(data)

In general, it is cleaner for a function to avoid transforming its parameters and instead return a new value. If you do need the function to transform an object in-place then probably avoid also returning the same object, as this could lead to confusion.

  • Related