I am using a library that returns a a series of ints using a parameter that looks like:
int ** outList
What is the best way to take that and wrap it in a bunch of NSNumber objects (and perhaps an NSArray to hold them)?
There is no shortcut, that I know of. You can write something like this:
int **outList = ...
int count = ...
NSMutableArray *result = [[NSMutableArray alloc] initWithCapacity:count];
for (int idx = 0; idx < count; idx++)
[result addObject:#(outList[idx])];
Hope it helps!
Related
I would like to do the following but Xcode can't make sense of duck[x]:
NSArray *duck1;
NSArray *duck2;
NSArray *duck3;
for ( int x=0; x < count; x++ ) {
duck[x]= #[[otherArrayOne objectAtIndex:x], [otherArrayTwo objectAtIndex:x], [otherArrayThree objectAtIndex:x], ];
}
but xCode doesn't like: 'duck[x]'
Xcode is right in prompting compile time error. Variable 'duck' is un-declared in your code.
You just have to declare 'duck' variable and initialize it. Add following lines after NSArray *duck3; variable declarations.
NSArray *duck = #[duck1,duck2,duck3];
int count = [duck count];
As above, I'm trying to create and then fill an array of structures with some starting data to then write to/read from.
I'm still writing the cache simulator as per my previous question:
Any way to get rid of the null character at the end of an istream get?
Here's how I'm making the array:
struct cacheline
{
string data;
string tag;
bool valid;
bool dirty;
};
cacheline **AllocateDynamicArray( int nRows, int nCols)
{
cacheline **dynamicArray;
dynamicArray = new cacheline*[nRows];
for( int i = 0 ; i < nRows ; i++ )
dynamicArray[i] = new cacheline [nCols];
return dynamicArray;
}
I'm calling this from main:
cacheline **cache = AllocateDynamicArray(nooflines,noofways);
It seems to create the array ok, but when I try to fill it I get memory errors, here's how I'm trying to do it:
int fillcache(cacheline **cache, int cachesize, int cachelinelength, int ways)
{
for (int j = 0; j < ways; j++)
{
for (int i = 0; i < cachesize/(cachelinelength*4); i++)
{
cache[i][ways].data = "EMPTY";
cache[i][ways].tag = "";
cache[i][ways].valid = 0;
cache[i][ways].dirty = 0;
}
}
return(1);
}
Calling it with:
fillcache(cache, cachesize, cachelinelength, noofways);
Now, this is the first time I've really tried to use dynamic arrays, so it's entirely possible I'm doing that completely wrong, let alone when trying to make it 2d, any ideas would be greatly appreciated :)
Also, is there an easier way to do write to/read from the array? At the moment (I think) I'm having to pass lots of variables to and from functions, including the array (or a pointer to the array?) each time which doesn't seem efficient?
Something else I'm unsure of, when I pass the array (pointer?) and edit the array, when I go back out of the function, will the array still be edited?
Thanks
Edit:
Just noticed a monumentally stupid error, it should ofcourse be:
cache[i][j].data = "EMPTY";
You should find your happiness. You just need the time to check it out (:
The way to happiness
First, i'm not a python programmer, so excuse my silly mistakes.
In C++ I have this public method from MyClass that creates a image dynamically and returns its size.
int MyClass::getImg(uchar *uimg[])
{
int size = variable_size;
*_uimg = new uchar[size];
memcpy(*_uimg, imageOrigin->data(), size);
uimg = _uimg;
return size;
}
And the boost:python:
BOOST_PYTHON_MODULE(mymodule)
{
class_<MyClass>("MyClass")
.def("getImg", &MyClass::getImg)
;
}
and when i try to use it in python:
def getImg():
img = c_char_p()
size = mymodule.MyClass.getImg(byref(img))
I'm getting this error:
Boost.Python.ArgumentError: Python argument types in
MyClass.getImg(MyClass, CArgObject, CArgObject)
did not match C++ signature:
getImg(class MyClass {lvalue}, unsigned char * *)
In python I also tried declaring
img = POINTER(c_ubyte)()
but that did'nt help either.
I googled it around for hours and i didn't came up with any good solution.
I just need access to that image in python, how can i get this done?
Revised and working version, exposing the data as a python list.
I am not sure how to implement this, but there may be a better way of implementing it, if you can choose your python interface freely. I think creating a list may be a better way to expose it. What do you expect from the return value? Maybe you can also wrap it a s a numpy array for better performance (there are also some questions on stackoverflow if you search for boost python and numphy)
class TestPtr
{
public:
int getImg(uchar **uimg)
{
int size = 9045;
uchar *_uimg = new uchar[size];
for( int i = 0; i < size; ++i )
_uimg[i] = i;
*uimg = _uimg;
return size;
}
};
boost::python::list getImgList( TestPtr &p )
{
uchar *uimg;
int rv = p.getImg(&uimg);
boost::python::list l;
for ( int i = 0; i < rv; ++i)
l.append( uimg[i] );
return l;
}
BOOST_PYTHON_MODULE(mymodule)
{
class_<TestPtr>("TestPtr")
.def("getImg",&getImgList)
;
}
Another hint, in your question, you have used the following line to call the method:
mymodule.MyClass.getImg()
This will make a class call (more or less equivalent to a static call) to your object. This is a mor ecorrect way to do it:
img = mymodule.MyClass()
data = img.getImg()
Suppose I have bunch of numbers. I have to first put the least significant digit into the corresponding bucket. Ex: 530 , I have to first put into the bucket 0. For number 61, I have to put into bucket 1.
I planned to use a multidimensional array to do this. So I create a 2-dimenional array, which nrows is 10 ( for 0~ 9) and ncolumns is 999999 ( because I don't know how large will the list be):
int nrows = 10;
int ncolumns = 999999;
int **array_for_bucket = (int **)malloc(nrows * sizeof(int *));
for(i = 0; i < nrows; i++)
array_for_bucket[i] = (int *)malloc(ncolumns * sizeof(int));
left = (a->value)%10;
array_for_bucket[left][?? ] = a->value;
Then I created one node call a. In this node a, there is a value 50. To find out which bucket I want to put it in, I calculate "left" and I got 0. So I want to put this a-> value into bucket 0. But now I am stuck. How do I put this value into the bucket? I have to use a pointer array to do this.
I thought for a long time but still couldn't find a good way to do it. So please share some ideas with me. thank you!
There is a much easier way of doing this, and instead of radix*nkeys space you only need an nkeys-sized buffer.
Allocate a second buffer that can fit nkeys keys. Now do a first pass through your data and simply count how many keys end up in each bucket. You now can create a radix-sized array of pointers where each pointer is to the start of that bucket in the output buffer. Finally, the second pass though the data moves the keys. Every time you move a key, increment that bucket pointer.
Here's some C code to make into C++:
void radix_sort(int *keys, int nkeys)
{
int *shadow = malloc(nkeys * sizeof(*keys));
int bucket_count[10];
int *bucket_ptrs[10];
int i;
for (i = 0; i < 10; i++)
bucket_count[i] = 0;
for (i = 0; i < nkeys; i++)
bucket_count[keys[i] % 10]++;
bucket_ptrs[0] = shadow;
for (i = 1; i < 10; i++)
bucket_ptrs[i] = bucket_ptrs[i-1] + bucket_count[i-1];
for (i = 0; i < nkeys; i++)
*(bucket_ptrs[keys[i] % 10]++) = keys[i];
//shadow now has the sorted keys
free(shadow);
}
But I may have misunderstood the question. If you are doing something a little different than radix sort, pleas add some details.
Look the Boost Pointer containers library if you want to store pointers.
C++ isn't my forte but this code from wikipedia-Raidx Sort is very comprehensive and probably is more C++-ish than what you've implemented so far. Hope it helps
This is C++, we don't use malloc anymore. We use containers. A two-dimensional array is a vector of vectors.
vector<vector<int> > bucket(10);
left = (a->value)%10;
bucket[left].push_back(a->value);
How do I assign a sequence of character strings to a char ** argv variable in a program? Its a command line argument. I'm currently trying to convert an .exe app to a dll.
For example:
{ "string1", "string2", "string3" } --- > char ** argv variable
My problem is somehow realted to this:
How does an array of pointers to pointers work? but I can't get it to work using the snippet shown there. Help!
const char* argv[] = {"string1", "string2", "string3", 0};
If the arguments aren't compile time constants I would do something like:
std::vector<const char*> arguments;
arguments.push_back(somePointer);
arguments.push_back(someOtherPointer);
arguments.push_back(0);
const char** argv = &arguments[0];
EDIT: Using PaxDiablos information that an argv-array should be null terminated.
what about getopt?
Note that Andreas Brincks answer is really what you want to do, where vector does all the heavy lifting of allocation and provides exception safety. I strongly suggest that you look into changing whatever reason there is for not being able to use vector. But if you really really cannot do so, I guess you could do something along the lines of the below code:
int numArgs = YOUR_NUMBER_HERE;
char **myArgv = new char*[numArgs+1];
for (int i=0; i<numArgs; ++i) {
myArgv[i] = new char[at least size of your argument + 1];
strncpy(myArgv[i], whereever your string is, buffer size);
myArgv[buffer size] = '\0';
}
myArgv[numArgs] = NULL;
// use myArgv here
// now you need to manually free the allocated memory
for (int i=0; i<numArgs; ++i) {
delete [] myArgv[i];
}
delete [] myArgv;