I have managed class with function:
int DoSomething(cli::array<int>^ values) { .. }
In DoSomething I must call native function:
template <class It>
int Calculate(It beg, It end) {..}
Which iterator to use?
You'll want to use a pinning pointer to the managed array. This will fix the array in memory (i.e. make it so the garbage collector can't move it) and then you can treat it as a native array. Below is a sample using your methods.
Take note, that you need to finish using the array before the pinning pointer goes out of scope--once the pinning pointer goes out of scope, the managed array is no longer pinned, and the garbage collector is free to move the array.
Also, take note that pinning the first element of the array causes the entire managed array to be pinned (in general using a pinning pointer on one part of a managed object causes the entire managed object to be pinned).
template <class It> int Calculate(It beg, It end)
{
int sum = 0;
for (; beg != end; ++beg)
{
int i = *beg;
sum += i;
}
return sum;
}
int DoSomething(cli::array<int>^ values)
{
int numValues = values->Length;
pin_ptr<int> pNativeValuesBegin = &values[0];
int * pBegin = pNativeValuesBegin;
int * pEnd = pBegin + numValues;
return Calculate(pBegin, pEnd);
}
int main(array<System::String ^> ^args)
{
array<int> ^ values = gcnew array<int> { 1, 2, 3, 4, 5 };
int sum = DoSomething(values);
System::Console::WriteLine(sum);
return 0;
}
Related
I want to define a constant array of constants at every MPI node using C++03. M_chunk_sizes defines the size of matrix that will be passed to other nodes and won't be changed during the runtime.
int* define_chunk_sizes( int S, int world) {
int out[world];
double quotient = static_cast<double> (S) / world;
int maj = ceil(quotient);
for (int i =0; i < world - 1; i++)
out[i] = maj;
out[world-1] = maj + (S - maj*world);
return out;
}
int main() {
const int M = 999; // rows
int world_size = 4;
const int* const M_chunk_sizes = define_chunk_sizes(M, world_size);
}
But i get a warning: address of stack memory associated with local variable 'out' returned [-Wreturn-stack-address]
return out;.
What is the right way of doing this?
funciton local variables(stack varibales) will go out of scope and life once function returns.
you have use dynamic memory management operators, so allocate memory to out using
new
and relase memory using
delete
once you done with it.
I keep getting this error in the console:
Unhandled exception: System.NullReferenceException
Here's the code:
class Car {
public:
int X;
int Y;
};
class SpecificCar : public Car {
};
class Container {
public:
int AmountOfCars = 0;
Car **cars = nullptr;
void AddCar(Car *ptr);
};
void Container::AddCar(Car *ptr) {
if(AmountOfCars == 0) {
cars[0] = ptr; //Debbuger says that the problem in question is located here
AmountOfCars++;
}
int main() {
Container container;
Car *ptr = new SpecificCar;
ptr->X = 1;
ptr->Y = 5;
container.AddCar(ptr);
}
While your Container by design isn't storing Cars, it still has to store pointers to cars. You'll have to come up with a method. The Standard offers std::vector<Car> as well as std::vector<Car*> but you're free to come up with anything else. Still, if you don't want the Standard methods, it's really up to you what else you want to do.
Car **cars is not a dynamic container, it's a pointer to a memory region. What you did there is just utterly wrong. You still have to allocate an array of pointers to be able to fill data there, such as
cars = new Car*[5];
With that you can address with indices from 0 to 4 inside array cars[]. Yet again this is not dynamic, your best bet is an std::vector<Car*>, if you want to go your own ways then malloc()/realloc(), maybe linked listing if you really want to bother with it.
The problem is that, in class Container, you defined a member cars initialized to nullptr.
The best way to fix the issue is to use a std::vector<Car*> for cars. If you absolutely don't want to use a vector (why ?), in class Container, you may replace:
Car **cars = nullptr;
by something like:
static const int MAX_AMOUNT_OF_CARS = 100;
Car* cars[MAX_AMOUNT_OF_CARS];
which will define a proper array of Car*; then, you will be able to use cars[0], cars[i], ...
I figure you're trying to teach yourself about memory management. I've rewritten your class and AddCar() to be more what you want. Accessing or removing a car and deleting the container are left as an exercise for the student. (Look at this as pseudo-code. I haven't compiled or run it.)
class Container
{
Car ** cars_ = nullptr;
int capacity_ = 0; // how much room we have for car pointers
int AmountOfCars_ = 0; // how many car pointers we actually contain
public:
int AmountOfCars() const { return AmountOfCars_; }
void AddCar(Car *ptr);
};
void Container::AddCar(Car *ptr)
{
if ( AmountOfCars_ + 1 > capacity_ ) // ensure we have capacity for another Car *
{
if ( capacity_ == 0 ) // if we have none set to 2, so we'll initially allocate room for 4
capacity_ = 2;
int newcapacity = capacity_ * 2; // double the capacity
Cars ** newcars = new Car*[ newcapacity ]; // allocate a new pointer array
memcpy( newcars, cars_, capacity_ * sizeof(Car*) ); // we're just moving pointers
delete cars_; // get rid of the old pointer array
cars_ = newcars; // point to the new pointer array
capacity_ = newcapacity; // update the capacity
}
++AmountOfCars_; // increase the number of cars
cars[ AmountOfCars_ ] = ptr; // and copy the pointer into the slot
}
In my program, I store objective-c objects in a c array, like this
va_start(list, o);
retval->objs = malloc(SIZE * count);
retval->objs[0] = (__bridge void *)o;
for (int i = 1; i < count; i++)
{
id o = va_arg(list, id);
retval->objs[i] = (__bridge void *)o;
}
va_end(list);
(count is a number containing how many objects will be added; that value is always correct)
objs is a void ** and is part of retval, which is a pointer to a struct. As of now, SIZE is defined as 100. Increasing and decreasing that had no effect.
As you can see, I bridge o to a void *, as I have to. objs, when all the objects are added, contains 3 objective-c objects. When I try to access a value like this
void *obj = CLArrayObjectAtIndex(_arr, ind);
return (__bridge id)obj;
this is the CLArrayObjectAtIndex() function
void *CLArrayObjectAtIndex(CLArrayType *arr, int ind)
{
void *o = arr->objs[ind];
if (o)
return o;
else
perror("Attempt to access NULL object or index out of bounds."), abort();
}
if the index (ind) is 0, it works. If the index is 1, the program crashes when it returns in main. If the index is 2, the program crashes as soon as I try to access it. If the index is 1, the value returned above is correct, but when the program crashes on return it is nil.
If the index is 1, the EXC_BAD_ACCESS code is 1; if the index is 2, the code is EXC_I386_GPFLT, a general protection fault. I already checked here for an explanation of this exception, although I couldn't find anything helpful. So, does anybody see why this error may be occurring?
when you store obj-c objects in C array don't just bridge cast them since that way arc doesn't know they are still used and releases them. __bridge_retain them so they stay around later, when you free the array __bridge_transfer them to give them back to ARC
also don't define size as 100.. sizeof(id) should work. You only need to store pointers
(Objective C Code)
int i=5;
{
int i=i;
NSLog(#"Inside Scope: %i",i);
}
NSLog(#"Outside Scope: %i",i);
Prints:
3385904 (Garbage)
5
replacing int i = i; with int i= 10; prints correctly... (Inside the scope's i)
Such as:
10
5
And (This code alone)
int i=i;
Compiles, but segfaults immediately.
How are any of these syntax's valid? What use are they, or are they compiler bugs that should have been caught earlier?
Is there any situation where it is necessary for using the same variable names inside a new scope under a new type, and how would you differentiate?
My only thoughts is could be the for() loop, as the compiler would be upset you're redefining int i; twice if you have two loops.
Because you're redefining i, you're setting i to the value for itself that hasn't been set yet.
Simply turning this:
int i=5;
{
int i=i;
}
into this:
int i = i;
//int i=5;
//{
//int i=i;
//}
will give you the same varied results. This problem has nothing to do with scope.
I am trying to compare two long bytearrays in VB.NET and have run into a snag. Comparing two 50 megabyte files takes almost two minutes, so I'm clearly doing something wrong. I'm on an x64 machine with tons of memory so there are no issues there. Here is the code that I'm using at the moment and would like to change.
_Bytes and item.Bytes are the two different arrays to compare and are already the same length.
For Each B In item.Bytes
If B <> _Bytes(I) Then
Mismatch = True
Exit For
End If
I += 1
Next
I need to be able to compare as fast as possible files that are potentially hundreds of megabytes and even possibly a gigabyte or two. Any suggests or algorithms that would be able to do this faster?
Item.bytes is an object taken from the database/filesystem that is returned to compare, because its byte length matches the item that the user wants to add. By comparing the two arrays I can then determine if the user has added something new to the DB and if not then I can just map them to the other file and not waste hard disk drive space.
[Update]
I converted the arrays to local variables of Byte() and then did the same comparison, same code and it ran in like one second (I have to benchmark it still and compare it to others), but if you do the same thing with local variables and use a generic array it becomes massively slower. I’m not sure why, but it raises a lot more questions for me about the use of arrays.
What is the _Bytes(I) call doing? It's not loading the file each time, is it? Even with buffering, that would be bad news!
There will be plenty of ways to micro-optimise this in terms of looking at longs at a time, potentially using unsafe code etc - but I'd just concentrate on getting reasonable performance first. Clearly there's something very odd going on.
I suggest you extract the comparison code into a separate function which takes two byte arrays. That way you know you won't be doing anything odd. I'd also use a simple For loop rather than For Each in this case - it'll be simpler. Oh, and check whether the lengths are correct first :)
EDIT: Here's the code (untested, but simple enough) that I'd use. It's in C# for the minute - I'll convert it in a sec:
public static bool Equals(byte[] first, byte[] second)
{
if (first == second)
{
return true;
}
if (first == null || second == null)
{
return false;
}
if (first.Length != second.Length)
{
return false;
}
for (int i=0; i < first.Length; i++)
{
if (first[i] != second[i])
{
return false;
}
}
return true;
}
EDIT: And here's the VB:
Public Shared Function ArraysEqual(ByVal first As Byte(), _
ByVal second As Byte()) As Boolean
If (first Is second) Then
Return True
End If
If (first Is Nothing OrElse second Is Nothing) Then
Return False
End If
If (first.Length <> second.Length) Then
Return False
End If
For i as Integer = 0 To first.Length - 1
If (first(i) <> second(i)) Then
Return False
End If
Next i
Return True
End Function
The fastest way to compare two byte arrays of equal size is to use interop. Run the following code on a console application:
using System;
using System.Runtime.InteropServices;
using System.Security;
namespace CompareByteArray
{
class Program
{
static void Main(string[] args)
{
const int SIZE = 100000;
const int TEST_COUNT = 100;
byte[] arrayA = new byte[SIZE];
byte[] arrayB = new byte[SIZE];
for (int i = 0; i < SIZE; i++)
{
arrayA[i] = 0x22;
arrayB[i] = 0x22;
}
{
DateTime before = DateTime.Now;
for (int i = 0; i < TEST_COUNT; i++)
{
int result = MemCmp_Safe(arrayA, arrayB, (UIntPtr)SIZE);
if (result != 0) throw new Exception();
}
DateTime after = DateTime.Now;
Console.WriteLine("MemCmp_Safe: {0}", after - before);
}
{
DateTime before = DateTime.Now;
for (int i = 0; i < TEST_COUNT; i++)
{
int result = MemCmp_Unsafe(arrayA, arrayB, (UIntPtr)SIZE);
if (result != 0) throw new Exception();
}
DateTime after = DateTime.Now;
Console.WriteLine("MemCmp_Unsafe: {0}", after - before);
}
{
DateTime before = DateTime.Now;
for (int i = 0; i < TEST_COUNT; i++)
{
int result = MemCmp_Pure(arrayA, arrayB, SIZE);
if (result != 0) throw new Exception();
}
DateTime after = DateTime.Now;
Console.WriteLine("MemCmp_Pure: {0}", after - before);
}
return;
}
[DllImport("msvcrt.dll", CallingConvention = CallingConvention.Cdecl, EntryPoint="memcmp", ExactSpelling=true)]
[SuppressUnmanagedCodeSecurity]
static extern int memcmp_1(byte[] b1, byte[] b2, UIntPtr count);
[DllImport("msvcrt.dll", CallingConvention = CallingConvention.Cdecl, EntryPoint = "memcmp", ExactSpelling = true)]
[SuppressUnmanagedCodeSecurity]
static extern unsafe int memcmp_2(byte* b1, byte* b2, UIntPtr count);
public static int MemCmp_Safe(byte[] a, byte[] b, UIntPtr count)
{
return memcmp_1(a, b, count);
}
public unsafe static int MemCmp_Unsafe(byte[] a, byte[] b, UIntPtr count)
{
fixed(byte* p_a = a)
{
fixed (byte* p_b = b)
{
return memcmp_2(p_a, p_b, count);
}
}
}
public static int MemCmp_Pure(byte[] a, byte[] b, int count)
{
int result = 0;
for (int i = 0; i < count && result == 0; i += 1)
{
result = a[0] - b[0];
}
return result;
}
}
}
If you don't need to know the byte, use 64-bit ints that gives you 8 at once. Actually, you can figure out the wrong byte, once you've isolated it to a set of 8.
Use BinaryReader:
saveTime = binReader.ReadInt32()
Or for arrays of ints:
Dim count As Integer = binReader.Read(testArray, 0, 3)
Better approach... If you are just trying to see if the two are different then save some time by not having to go through the entire byte array and generate a hash of each byte array as strings and compare the strings. MD5 should work fine and is pretty efficient.
I see two things that might help:
First, rather than always accessing the second array as item.Bytes, use a local variable to point directly at the array. That is, before starting the loop, do something like this:
array2 = item.Bytes
That will save the overhead of dereferencing from the object each time you want a byte. That could be expensive in Visual Basic, especially if there's a Getter method on that property.
Also, use a "definite loop" instead of "for each". You already know the length of the arrays, so just code the loop using that value. This will avoid the overhead of treating the array as a collection. The loop would look something like this:
For i = 1 to max Step 1
If (array1(i) <> array2(i))
Exit For
EndIf
Next
Not strictly related to the comparison algorithm:
Are you sure your bottleneck is not related to the memory available and the time used to load the byte arrays? Loading two 2 GB byte arrays just to compare them could bring most machines to their knees. If the program design allows, try using streams to read smaller chunks instead.