The code presented here is simple to illustrate a use case. I want to know the efficient ways of passing an array of num to C from Raku.
#include <stdio.h>
#include <omp.h>
void c_sum_two(double *first, double *second, double *third, int num)
{
#pragma omp parallel for
for (int i = 0; i < num; i++)
{
third[i] = first[i] + second[i];
}
}
What this does is: passes first and second array from Raku to C, performs some calculation, in this case (addition using openmp) and returns a num array to raku.
use NativeCall;
constant MYDYN = "./testsum.dll";
sub c_sum_two(CArray[num64], CArray[num64],CArray[num64], int32)
is native( MYDYN) { * };
sub native_sum_two(@arr_one is copy, @arr_two is copy) {
my $elems = @arr_one.elems;
##======================================================##
# check if two array have same elems
##======================================================##
# Prepare arrays for passing to C
##======================================================##
@arr_one = @arr_one.map: {$_.Num};
@arr_two = @arr_two.map: {$_.Num};
# handling first array
my $first = CArray[num64].new(@arr_one);
# handling second array
my $second = CArray[num64].new(@arr_two);
##======================================================##
# Prepare for return array
my $return = CArray[num64].allocate($elems);
##======================================================##
# Call the C function
c_sum_two($first, $second, $return, $elems);
##======================================================##
# Get the output back
$return.list
}
my @a = <1.2 2 3.2 10 0.33>;
my @b = <2 12 18 10 8>;
say native_sum_two(@a, @b) # (3.2 14 21.2 20 8.33)
While preparing for passing arrays to C, I am converting each value of two arrays to Num (O(n) + O(n) time).
- Is this the right efficient way of doing this?
- Is there other way to directly lay the array as num in memory?
- Also is there another better way of returning array?
May be due to the overhead, I am not getting the speedup compared to the same thing in raku:
my @c;
for [email protected] {
@c[$_] = @a[$_] + @b[$_];
}
say @c
you can avoid creating the intermediate Num arrays and use the NativeCall CArray constructor with your original arrays directly.