I have a Python dictionary in my Selenium script in which one of the keys ("data") is updated afterwards because it's not a fixed value, so I get it with Selenium:
fields_personal = {
"data": "",
"nome": "João da Silva",
"documento": "CPF",
"numero": "123.456.789-10",
"telefone": "(01)23456-7890",
"email": "teste#email.com"
}
for data, value in fields_personal.items():
element = driver.find_element_by_id(data)
element.send_keys(value)
if data == "data":
for item in element.find_elements_by_tag_name("option"):
option = item.text.strip()
elem = driver.find_element_by_xpath("//*[#id='data']/option[1]").click()
fields_personal["data"] = option
break
print("{}: {}".format(data, value))
No problem with that, it works fine. But when I try to print the dictionary with print("{}: {}".format(data, value)), or simply print(data, value) it prints "data" key with empty value, as if it hasn't been updated:
data:
nome: João da Silva
documento: CPF
numero: 123.456.789-10
telefone: (01)23456-7890
email: teste#email.com
The only way I can print the updated dictionary is calling pprint.pprint(fields_personal), since I want it structured line by line, but this outputs the result formatted with quotes and curly braces, which I don't want:
{'data': '28/06/2021',
'documento': 'CPF',
'email': 'teste#email.com',
'nome': 'João da Silva',
'numero': '123.456.789-10',
'telefone': '(01)23456-7890'}
So, how can I print it line by line, without quotes and curly braces and updated?
In your if block, you updates fields_personal["data"]; however, when you print it as data, this is the original value read at the start of for loop.
You can move your print inside the block, adding an else to the if to not print two times the same value.
for data, value in fields_personal.items():
element = driver.find_element_by_id(data)
element.send_keys(value)
if data == "data":
for item in element.find_elements_by_tag_name("option"):
option = item.text.strip()
elem = driver.find_element_by_xpath("//*[#id='data']/option[1]").click()
fields_personal["data"] = option
break
print("{}: {}".format("data", fields_personal["data"])
else:
print("{}: {}".format(data, value))
However, if you can just wait after the for block, it would be better.
for data, value in fields_personal.items():
element = driver.find_element_by_id(data)
element.send_keys(value)
if data == "data":
for item in element.find_elements_by_tag_name("option"):
option = item.text.strip()
elem = driver.find_element_by_xpath("//*[#id='data']/option[1]").click()
fields_personal["data"] = option
break
for key, value in fields_personal.items():
print(f"{key}: {value}")
Related
I am searching for a different way to access every key in a dictionary within a for loop. Underneath, there is an example code, where I iterate through a dictionary and access every key with the help of a counter and a if statement. Is there another way to access the keys, without a counter or an if statement?
def string_to_dict(csv):
dict = []
tmp = csv.splitlines()
for i in tmp:
tmp_dict = {"vorname" : "none", "nachname" : "none", "email" : "none"};
tmp_i= i.split(",")
counter = 0;
for si in tmp_i:
if counter ==0:
tmp_dict["vorname"] = si
counter =counter + 1
elif counter == 1:
tmp_dict["nachname"] = si
counter = counter + 1
else:
tmp_dict["email"] = si
dict.append(tmp_dict)
csv = """Donald,Duck,d.duck#entenhausen.com
Wiley,Coyote,whiley#canyon.org
Road,Runner,roadrunner#canyon.org"""
There is no need for the loop if you already expect name, surname and email.
def string_to_dict(csv):
dict = []
tmp = csv.splitlines()
for i in tmp:
tmp_dict = {"vorname" : "none", "nachname" : "none", "email" : "none"};
tmp_i= i.split(",")
tmp_dict["vorname"] = tmp_i[0]
tmp_dict["nachname"] = tmp_i[1]
tmp_dict["email"] = tmp_i[2]
dict.append(tmp_dict)
We can keep iterating to improve the solution:
def string_to_dict(csv):
dict = []
tmp = csv.splitlines()
for i in tmp:
tmp_dict = {"vorname" : None, "nachname" : None, "email" : None};
tmp_i= i.split(",")
tmp_dict["vorname"] = tmp_i[0]
tmp_dict["nachname"] = tmp_i[1]
tmp_dict["email"] = tmp_i[2]
dict.append(tmp_dict)
And even more (if you want to use a protected keyword like dict, naming convention is to use an underscore after it):
def string_to_dict(csv):
dict_ = []
for line in csv.splitlines():
vor_name, nach_name, email = line.split(",")
dict_.append({"vorname" : vor_name, "nachname" : nach_name, "email" : email})
return dict_
And with list comprehensions:
def string_to_dict(csv):
def _parse_item(vor_name, nach_name, email):
return {"vorname" : vor_name, "nachname" : nach_name, "email" : email}
return [_parse_item(*line.split(",")) for line in csv.splitlines()]
If you want minimal changes to what you have done so far, you can just get list of keys and use the index value (counter variable in your case), something like this:
for i in tmp:
tmp_dict = {"vorname" : "none", "nachname" : "none", "email" : "none"};
tmp_i= i.split(",")
counter = 0;
keys = [*temp_dict.keys()] # List of Keys
for si in tmp_i:
tmp_dict[keys[counter]] = si # Key at index counter
counter += 1
dict.append(tmp_dict)
Sample Run:
>>string_to_dict(csv)
[{'vorname': ' Road', 'nachname': 'Runner', 'email': 'roadrunner#canyon.org'}, {'vorname': ' Road', 'nachname': 'Runner', 'email': 'roadrunner#canyon.org'}, {'vorname': ' Road', 'nachname': 'Runner', 'email': 'roadrunner#canyon.org'}]
Another Note: You're naming the variable as dict You should avoid that since it's a keyword in Python
Lets start with the fact that you are not trying to iterate over a dictionary but to create a list containing dictionary entries from a CSV format string.
secondly there are a lot of python syntactic mistakes and errors in your code.
Refrain from using reserved word such as "dict" as parameter names.
You can use this code snippet as a start if it helps you but I recommend brushing up on python syntax and best practices.
result = []
for line in csv.splitlines():
vorname, nachname, email = line.split(",")
result.append(
{"vorname": vorname.strip(), "nachname": nachname.strip(), "email": email.strip()})
This can be done also using list comprehension, but is much less readable
I have searched quite thoroughly and have not found a suitable solution. I am new to Python/Programming, so I appreciate any advice I can get:
I am trying to search a string from StringSet, here is what i am trying to do but not getting the value.
string_set = {'"123", "456", "789"'}
value = '123'
values_list = []
def fun():
for i in string_set:
if i in value:
output=LookupTables.get('dynamo-table', i, {})
return output
fun()
Using the above if it value is in the stringset then it will return the value which is in my dynmodb table.
Nothe: There could be more than 5000 values in my table so i wanted to get earliest possible return.
maybe you should romove the extra '' firstly
string_set = {'"123", "456", "789"'} # this set has just one value '"123", "456", "789"'
string_set_fixed = {"123", "456", "789"}
im assuming you're just checking if 123 is in "123", "456", "789" since you had it wrapped in single quotes:
to represent that lets use:
strset = {"123", "456", "789"}
what if you have to use that weird variable?
this should render it useable
strset = {'"123", "456", "789"'}
removed = next(iter(strset))
strset.update((removed).split())
strset.remove(removed)
strset = set([i.strip(",").strip('"') for i in strset])
another cleaner way:
strset = {'"123", "456", "789"'}
exec(f"strset = {next(iter(strset))}")
print("123" in strset)
now to check if value is in there:
if value in strset:
#do code here
Try this:
string_set = {"123", "456", "789"}
value = '123'
values_list = []
def fun():
if value in string_set:
output = LookupTables.get('dynamo-table', value, {})
return output
fun()
Explanation:
Your definition of string_set contains an extraneous pair of ' ';
When you are testing i in value, you are comparing i against all substrings of value, rather than against the whole string.
The following code works on python without any issue. It opens the JSON file, and replace all bananas to apples:
import json
replacements = "banana" : "apple"
with open(mycodepath, 'r') as file:
data = file.read()
for old, new in replacements.items():
data = data.replace(old, new)
However, I want to replace "ArmReoriented", "visible": true with "ArmReoriented", "visible": false,
I tried using triple quotes, but it does not work.
replacements = """ArmReoriented", "visible": true""" : """ArmReoriented", "visible": false,"""
How I replace a text containing quotes on JSON using Python?
Using """ is basically a comment or a doc-string and would not work.
Put double quote between a single quote string like below.
replacements = {'"ArmReoriented", "visible": true' : '"ArmReoriented", "visible": false'}
Try switching to single quotes in your replacements dict:
replacements = {'"ArmReoriented", "visible": true': '"ArmReoriented", "visible": false,'}
data = 'asd asd asd "ArmReoriented", "visible": true asd asd'
for old, new in replacements.items():
data = data.replace(old, new)
print(data)
You also may escape double quotes both from key and from value in your replacement dict:
replacements = {"\"ArmReoriented\", \"visible\": true": "\"ArmReoriented\", \"visible\": false,"}
If we know what key the value ArmReoriented is attached to, we can do this the right way, processing your content structured data rather than as a string:
import json, copy
def hideReorientedArm(obj):
if isinstance(obj, dict):
if obj.get("LastEvent") == "ArmReoriented" and obj.get("visible") is True:
obj["visible"] = False
return obj
def walk(obj, updateFn):
if isinstance(obj, list):
obj = [walk(elem, updateFn) for elem in obj]
elif isinstance(obj, dict):
obj = {k: walk(v, updateFn) for k, v in obj.items()}
return updateFn(obj)
with open(mycodepath, 'r') as file:
data = json.load(file)
data = walk(data, hideReorientedArm)
See this running at https://ideone.com/Zr6546
Even if you don't know the name of the specific key having that value, you can still search all of them if that's necessary for some reason, replacing the shorter hideReorientedArm definition above with something more like the following:
def hideReorientedArm(obj):
if isinstance(obj, dict):
if obj.get("visible") is True:
foundArmReoriented = False
for (k,v) in obj.items():
if v == "ArmReoriented":
foundArmReoriented = True
break
if foundArmReoriented:
obj["visible"] = False
return obj
...see this version running at https://ideone.com/z34Mx1
Print statement not printing anything on console in python.
I am printing the key, value of the JSON file where the key starts with #id
found = False
for key, di in json.loads(json_data).iteritems():
for k, v in di.items():
if k.startswith('#id'):
found = True
print k, v
sys.stout.flush()
break
if found:
break
I think have done a mistake. Any help will be appreciated.
Given the sample data you provided in the comment section, you can try this:
import json
json_data = '{ "nvd": { "entry": [ { "#id": "CVE-2016-0001", "vuln:cve-id": "CVE-2016-0001", "vuln:published-datetime": "2017-05-11T10:29:55.767-04:00", "vuln:last-modified-datetime": "2017-05-11T10:29:55.767-04:00", "vuln:summary": "** REJECT ** DO NOT USE THIS CANDIDATE NUMBER. " }]}}'
wantedKey = "#id"
found = False
for key, di in json.loads(json_data).items():
if wantedKey in di['entry'][0]:
found = True
print(wantedKey + " : " + di['entry'][0][wantedKey])
break
Output:
#id : CVE-2016-0001
After the end of my code, I have a dictionary like so:
{'"WS1"': 1475.9778073075058, '"BRO"': 1554.1437268304624, '"CHA"': 1552.228925324831}
What I want to do is to find each of the keys in a separate file, teams.txt, which is formatted like this:
1901,'BRO','LAD'
1901,'CHA','CHW'
1901,'WS1','MIN'
Using the year, which is 1901, and the team, which is the key of each item in the dictionary, I want to create a new dictionary where the key is the third column in teams.txt if the year and team both match, and the value is the value of the team in the first dictionary.
I figured this would be easiest if I created a function to "lookup" the year and the team, and return "franch", and then apply that function to each key in the dictionary. This is what I have so far, but it gives me a KeyError
def franch(year, team_str):
team_str = str(team_str)
with open('teams.txt') as imp_file:
teams = imp_file.readlines()
for team in teams:
(yearID, teamID, franchID) = team.split(',')
yearID = int(yearID)
if yearID == year:
if teamID == team_str:
break
franchID = franchID[1:4]
return franchID
And in the other function with the dictionary that I want to apply this function to:
franch_teams={}
for team in teams:
team = team.replace('"', "'")
franch_teams[franch(year, team)] = teams[team]
The ideal output of what I am trying to accomplish would look like:
{'"MIN"': 1475.9778073075058, '"LAD"': 1554.1437268304624, '"CHW"': 1552.228925324831}
Thanks!
Does this code suite your needs?
I am doing an extra check for equality, because there were different string signs in different parts of your code.
def almost_equals(one, two):
one = one.replace('"', '').replace("'", "")
two = two.replace('"', '').replace("'", "")
return one == two
def create_data(year, data, text_content):
""" This function returns new dictionary. """
content = [line.split(',') for line in text_content.split('\n')]
res = {}
for key in data.keys():
for one_list in content:
if year == one_list[0] and almost_equals(key, one_list[1]):
res[one_list[2]] = data[key]
return res
teams_txt = """1901,'BRO','LAD'
1901,'CHA','CHW'
1901,'WS1','MIN'"""
year = '1901'
data = { '"WS1"': 1475.9778073075058, '"BRO"': 1554.1437268304624, '"CHA"': 1552.228925324831 }
result = create_data(year, data, teams_txt)
And the output:
{"'CHW'": 1552.228925324831, "'LAD'": 1554.1437268304624, "'MIN'": 1475.9778073075058}
Update:
To read from text file use this function:
def read_text_file(filename):
with open(filename) as file_object:
result = file_object.read()
return result
teams_txt = read_text_file('teams.txt')
You may try something like:
#!/usr/bin/env python
def clean(_str):
return _str.strip('"').strip("'")
first = {'"WS1"': 1475.9778073075058, '"BRO"': 1554.1437268304624, '"CHA"': 1552.228925324831}
clean_first = dict()
second = dict()
for k,v in first.items():
clean_first[clean(k)] = v
with open("teams.txt", "r") as _file:
lines = _file.readlines()
for line in lines:
_,old,new = line.split(",")
second[new.strip()] = clean_first[clean(old)]
print second
Which gives the expected:
{"'CHW'": 1552.228925324831, "'LAD'": 1554.1437268304624, "'MIN'": 1475.9778073075058}