eddelbuettel commented on issue #187:
URL:
https://github.com/apache/arrow-nanoarrow/issues/187#issuecomment-1821131310
I was wondering if you we could bring this back to the fore? I am currently
loosing my mind as a simple 'call from R' wrapper for the (nice) `linesplitter`
example works just fine when I start in R and pass an external pointer down:
```c++
// Plain Interface
// [[Rcpp::export]]
bool linesplit_from_R_plain(const std::string str, SEXP sxparr) {
// We get an R-created 'nanoarrow_array', an S3 class around an external
pointer
if (!Rf_inherits(sxparr, "nanoarrow_array"))
Rcpp::stop("Expected class 'nanoarrow_array' not found");
// It is a straight up external pointer so we can use R_ExternalPtrAddr()
struct ArrowArray* arr = (struct ArrowArray*)R_ExternalPtrAddr(sxparr);
auto res = linesplitter_read(str, arr);
return true;
}
```
But when I want to start from C++, I get lost somewhere build the
`nanoarrow`-compliant external pointer up by itself. It all works fine when I
cheat (as the `nanoarrow` package also does in places) and call into R:
```c++
// res <- linesplit_from_cpp("the\nquick\nbrown\nfox");
// print(res);
// print(arrow::Array$create(res))
//
// [[Rcpp::export]]
Rcpp::XPtr<ArrowArray> linesplit_from_cpp(const std::string str) {
Rcpp::Environment ns = Rcpp::Environment::namespace_env("nanoarrow");
Rcpp::Function f1 = Rcpp::Function("nanoarrow_array_init", ns);
Rcpp::Function f2 = Rcpp::Function("na_string", ns);
auto sxparr = f1(f2());
// It is an external pointer we can access, here with checking
auto arr = xptr_get_ptr<ArrowArray>(sxparr, "nanoarrow_array");
auto res = linesplitter_read(str, arr);
auto s = Rcpp::XPtr<ArrowArray>{sxparr};
// setting a tag somehow upsets the Arrow nature of things
//xptr_set_tag(s, Rcpp::wrap(XPtrTagType<ArrowArray>));
return s;
}
```
(Apologies for the small bits of `Rcpp` but that's I am most familiar with.
The helpers used above are minimal wrappers around the C API of R as eg the
following.)
```c++
template <typename T> Rcpp::XPtr<T> make_xptr(SEXP p) {
return Rcpp::XPtr<T>(p); // the default Rcpp::XPtr ctor with
deleter on and tag and prot nil
}
```
So far so good but I still have two problems. I can't seem to build an
external pointer 'up from the C/C++ bases' to make `nanoarrow` happy. It comes
out ok, but invoking any of the R-level helpers goes astray. A simple
`print(res)` or `print(str(res))` of the return object gets an error of a
failing allocation of a bazillion bytes. The other (smaller) problem is that I
good some use out of setting (and checking) external pointer tags, somehow
doing that here with the one gotten by calling into R also dirties some other
bit.
By now there are nice bits and pieces of `nanoarrow` use now in the `adbc*`
packages (and the repo), in `duckdb-r`, and possibly also in the geospatial
apps (haven't looked). The (vendorable) `nanoarrow.*` are fine _just_ C/C++
work. The R interface is fine for work at the REPL prompt. But there is much
less on 'how to work with `nanoarrow` for R extensions' (and ditto for Python
where support is slowly growing in the package). So would there be some
appetite to extend, say, what is in `nanoarrow.hpp` in light of possible
'interface helpers' ? I'd be happy to help along, of course.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: [email protected]
For queries about this service, please contact Infrastructure at:
[email protected]