My Python script app.py has this function for example:
def testmethod(x):
return {"steps":["hello","world"]}
I am using Python C-API in Objective-C as follows:
Py_Initialize();
PyObject *pName = PyUnicode_DecodeFSDefault("app");
PyObject* pModule = PyImport_Import(pName);
Py_DECREF(pName);
PyObject* myFunction = PyObject_GetAttrString(pModule,(char*)"testmethod");
PyObject* args = PyTuple_Pack(1,PyFloat_FromDouble(223.22));
PyObject* myResult = PyObject_CallObject(myFunction, args);
NSLog(@"Check for dict: %d",PyDict_Check(myResult)); // Prints true!!!!!!!!!!!! So definitely a dictionary
After this, I am not really sure how I can convert the myResult to retrieve my dictionary. For doubles and strings, we usually use the PyFloat_AsDouble and PyUnicode_AsUTF8String, PyBytes_AsString functions but I can't seem to find a PyBLAHBLAH_AsDict or equivalent method.
double result = PyFloat_AsDouble(myResult);
NSLog(@"Result: %f",result);*/
PyObject* pStrObj = PyUnicode_AsUTF8String(myResult);
char* zStr = PyBytes_AsString(pStrObj);
NSLog(@"String: %@",[NSString stringWithUTF8String:zStr]);
I don't have much experience with Objective-C so maybe I am not looking at the right place.
How can I convert the PyObject to a NSDictionary?
I am basically looking for a C way of accessing the dictionary first (a map for example) which I can then use Objective-C methods to convert to NSDictionary. Similar to how I used PyUnicode_AsUTF8String, PyBytes_AsString and stringWithUTF8String all combined together to get a NSString out of the Python String. Looking for something similar for dictionaries.
I have figured out a way to achieve this but I don't know if this is the best possible way of doing this. I modified my python script to use json.dumps to return a string representation of the dictionary. Then in my Objective-C code, I first get the string, then use JSONObjectWithData to convert the json string to a NSDictionary. This works for now but I am curious if there is a better way of doing this without having to return string instead of dictionary from Python. This seems more like a workaround solution to me. Here's what I have now:
app.py:
import json
def testmethod(x):
return json.dumps({"steps":["hello","world"]})
Objective-C:
Py_Initialize();
PyObject *pName = PyUnicode_DecodeFSDefault("app");
PyObject* pModule = PyImport_Import(pName);
Py_DECREF(pName);
PyObject* myFunction = PyObject_GetAttrString(pModule,(char*)"testmethod");
PyObject* args = PyTuple_Pack(1,PyFloat_FromDouble(223.22));
PyObject* myResult = PyObject_CallObject(myFunction, args);
PyObject* pStrObj = PyUnicode_AsUTF8String(myResult);
char* zStr = PyBytes_AsString(pStrObj);
NSString *jsonStr = [NSString stringWithUTF8String:zStr];
NSLog(@"String: %@",jsonStr);
NSError *error;
NSData *data = [jsonStr dataUsingEncoding:NSUTF8StringEncoding];
NSDictionary *dictionary = [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:&error];
NSLog(@"Dictionary: %@",dictionary);
PyUnicode_AsUTF8String,PyBytes_AsStringandstringWithUTF8Stringall combined together to get a NSString out of the Python String. Looking for something similar for dictionaries.