Adding new number of dictionary based on the value of other dictionaries - python

My main objective is as below:
(1) Calculate the number of "id", "id_value". Then find what which value is not present in "id_value" based on "id". Example, "id" = [1,2,3,4], "id_value"=[1,2]. Then add a new dictionary of "id_value" into the main({"id_value":3},{"id_value":4}).
I tried to use set to find the difference between value within these two variables but with error. Could anyone please assist me.
main = [ {
"y" : {
"a" : [ {
"u" : [ {
"y" : 0
"x" : [ {
"check" : {
"value" : 0
My code is as below:
forid= []
forvalueid= []
for x in main[0]["x"]:
for y in x["example"]:
forid.append(y["id"])
I am getting error for "lambda cannot contain assignment"... can I know why?
* I solved this Thank you for commenting

Not sure if that will produce what you intend, but this is the lambda free version of your current code:
def func(x):
y["id_value"] = x
map(func, addvalue(forvalueid))

Related

Mongodb Python: How to use $push overwrites existing value rather than adds to the end of an array within a document

I have a document like this
{ "_id" : 23, "local_id" : 1234, "global_id" : [ "P123", "P345" ] }
If I want to $push new value to the array has the key “global_id” then I can do this
collection.update_one({‘local_id’: l_pid}, {’$push’: {‘global_id’: "P678"}})
and the document looks sth like this , for example : (push P678 to the array)
{ “_id” : 23, “local_id” : 1234, “global_id” : [ “P123”, “P345”,
“P678” ] }
But next time when the same key of “global_id” comes in it keeps appending to the end of array like : (this time the same P678 comes in)
{ “_id” : 23, “local_id” : 1234, “global_id” : [ “P123”, “P345”,
“P678” , “P678”] }
I want it to overwrite to existing value, and the array has to have unique value, the value can’t be the same.
How can I do it?
Thanks
Base on #rickhg12hs answer, use $addToSet solve my issue
collection.update_one({‘local_id’: l_pid}, {’$addToSet’: {‘global_id’: "P678"}})

trying to update my MongoDB collection via Python (PyMongo) but my logic is wrong

I'm new to programming and I've been learning Flask for about a week now, trying to design an e-commerce website.
I have a collection called users, in which each entry looks like this
{
"_id" : ObjectId("5b9170f1c5eb754e3ab8917f"),
"username" : "suhas",
"password" : "suhas",
"email" : "suhas",
"account_type" : "buyer",
"cart" : [
{
"product_id" : "5b915dd3c5eb754278e160e7",
"quantity" : 7
},
{
"product_id" : "5b915e3fc5eb754278e160e8",
"quantity" : 3
}
]
}
and a users.products collection, one of the elements look like this
{
"_id" : ObjectId("5b915f02c5eb7544108a14b9"),
"product name" : "Laptop",
"price" : 50000,
"description" : "HP laptop",
"user_id" : "5b914fc3c5eb753eaf81770c",
"username" : "chiranth"
}
I wanted to add a feaure "add to cart" that adds the product_id and quantity into a cart(type list) as dictionaries, as seen in the db.users collection.
The code in Python I've written as:
cart_dict = user_info.get("cart")
for dict1 in cart_dict:
if dict1["product_id"]==product_id:
db["users"].update({"_id" : ObjectId(user_id),"cart.product_id":product_id},{ '$inc':{ 'cart.$.quantity':quantity}})
break
else:
db["users"].update({"_id":ObjectId(user_id)},{"$addToSet":{"cart":{"$each":[{"product_id":product_id,"quantity":quantity}]}}})
The problem is, however, that if I increment the second product by adding 2 more to the cart adding to the present 3, the if condition checks the first product, sees that product ID doesn't match and just adds it as a new product AND THEN moves to product 2.
So my question would be: how do I ask the if condition to check all product_id's first AND THEN, if none match, add the product?
EDIT : to clarify,
my issue is with the IF condition. I want it to first compare product A, if that isnt satisfied, move to product B, and IF neither match, THEN it should go to the else loop. How do i do that?
Hey the code you have provided, their is unnecessary second for loop on same data just above the if condition.
you should remove that line. As pr updating data the code i used and works is as :
collection.update({'_id':int(n)},{'$set' : {'CloseDate':TodayDate,'Status':'close'}})
in this the where is provided in _id and the fields CloseDate & Status are being updated, this works, so you should put your new values that are to be updated in DB in some variables and directly assign them in your documents name.
Hope this helps.

Python - add a list of dictionary in a dictionary

So I have a dictionary called component and a list of dictionaries called allocations.
I want to be able to put the allocations under a component as a nested dictionary. kind of like so:
Allocations[
allocation1 : {
key : value
},
allocation2 {
key : value
}
]
My desired output:
Component1 : {
key:value
allocations : [allocation1 : {
key : value
}
,allocation2 : {
key : value
}
]
}
I came from Java, and i realize there is no append that I can use.
I tried this and obviously didnt work:
#allocate this under the selected component - DIDNT WORK
component["allocations"][] = allocation
How can I create a list of dictionaries in a dictionary?
Simply assign it:
component["allocations"] = some_list
For instance, if you want a new, empty one:
component["allocations"] = []
or:
component["allocations"] = list()
Then, manipulate the list as usual:
component["allocations"].append(some_object)

Reach to array subdocument in mongodb

How to reach to the last element of scores array with score value: 64.8 ???
I try to use $pull operator,but I have 200 documents like this form. So, I can't make use of exact value of latest element of scores array.
{
"_id" : 198,
"name" : "Timothy Harrod",
"scores" : [
{
"type" : "exam",
"score" : 11.9075674046519
},
{
"type" : "quiz",
"score" : 20.51879961777022
},
{
"type" : "homework",
"score" : 55.85952928204192
},
{
"type" : "homework",
"score" : 64.85650354990375
} ]
}
Easiest way would be to put that document into a python dict if it's in string format:
import json
doc_json = json.loads(doc_string)
Then to access the LAST element of the scores array, just do:
last_element = doc_json['scores'][-1]
The ['scores'] tells us to get the 'scores' array from our json_doc, and the [-1] tells us to access the last element of this 'scores' array. From there, if you wanted the score from the last_element, you would just do:
last_score = last_element['score']
You could have also gotten it straight by doing:
last_score = doc_json['scores'][-1]['score']

Retrieve a single property from document

Good day everyone.
Suppose we have a collection and a document which looks something like this:
test_doc = {
"ID" : "123",
"a" : [
{
'x' : "/",
'y' : "2000",
'z' : "1000"
},
{
'x' : "/var",
'y' : "3500",
'z' : "3000"
}
]
}
What i need is to retrieve a single property a.z .
In MongoDB i'm using the following query:
db.testcol.find({"ID":"123","a.x":"/"},{'a.z':1})
which returns this:
{ "_id" : ObjectId("skipped"), "a" : [ { "z" : "1000" }, { "z" : "3000" } ] }
As you can see it returns all the z properties, but i need only the first one or the second when condition is {"ID":"123","a.x":"/var"}
So, the question is: how do i get a single property in this situation? Is it just a matter of bad design or should i somehow process the returned document in code (python)? Any suggestions will be much appreciated.
In MongoDB 2.0 and older, this is not possible. What you want to do is return a specific element of the array - but that is not what your projection is actually doing, it will just return the whole array and then the z element of each one.
However, with 2.2 (rc2 as of writing this answer), things have gotten a bit better. You can now use $elemMatch as part of your projection (see SERVER-2238 for details) so that you only pull back the required array element. So, try something like this:
db.foo.find({"ID":"123",'a':{$elemMatch:{'x':"/"}}},{_id : 0, 'a.$': 1})
//returns
{ "a" : [ { "x" : "/", "y" : "2000", "z" : "1000" } ] }
Or, just use $elemMatch in the projection itself, which you may think is cleaner:
db.foo.find({"ID":"123"},{_id : 0, 'a':{$elemMatch:{'x':"/"}}})
//returns
{ "a" : [ { "x" : "/", "y" : "2000", "z" : "1000" } ] }
So, now, at least the array returned is only the one containing only the entries you want and you can simply reference the relevant z element (elemMatch projections on a subdocument are not yet supported).
Last but not least, in 2.2 we have the aggregation framework, and one of the things it can do (with the $project operator, is to reshape your documents and change sub documents and array elements into top level arrays. To get your desired result, you would do something like this:
db.foo.aggregate(
{$match : {"ID":"123"}},
{$unwind : "$a"},
{$match : {"a.x":"/"}},
{$project : {_id : 0, z : "$a.z"}}
)
The result looks like this:
{ "result" : [ { "z" : "1000" } ], "ok" : 1 }

Categories