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]

Reply via email to