[R] allocating memory in a C module

Thomas Lumley tlumley at u.washington.edu
Sat Oct 4 02:06:32 CEST 2003


On Fri, 3 Oct 2003, Rajarshi Guha wrote:

> Hi,
>   I'm using a package that has a number of formats. I have C code to
> parse these formats the results of which are generally integer arrays.
>
> I would like to utilize these modules in R rather than writing R code to
> read in these files (and also to learn about R extensions).
>
> Essentially what I want is to do something like this:
>
> load_tsets <- function(t,c,p)
> .C( "c_load_tsets",
> as.integer(t),
> as.integer(c),
> as.integer(p))
>
> t,c,p should be R list objects

I think you mean vectors: as.integer() doesn't work on lists.

>				, and empty when supplied to the function
> load_tsets. On return each one will contain a list of integers. Thus in
> the C function I need to allocate storage for the 3 arrays.
>
> I've tried using Realloc but when I run the function the returned list
> does not show an increase in length.

No, it wouldn't.  You can't change the size of an object inside .C.
Since R has no way to find out how big the object is (C doesn't provide
such a facility), it must assume it is the same size that was passed in.


>
> Do I need to go to the .Call interface?

Yes.

> Is there any code that comes with the R distro (or if anybody has some
> similar code that I could look at)?

Here's some code that does a pointless example

In C:


#include "R.h"

/* function takes no arguments and returns an object */
SEXP pie(){

	int n;
	SEXP alist, avector;

	/* work out how long a list to return */
	n = 2;
	/* create the list */
	PROTECT(alist = allocVector(VECSXP, n));

	/* create the first vector and populate it */
	n = 4;
	PROTECT(avector = allocVector(INTSXP, n));
	INTEGER(avector)[0] = 3;
	INTEGER(avector)[1] = 1;
	INTEGER(avector)[2] = 4;
	INTEGER(avector)[3] = 1;
	/* stick it into the list */
	SET_VECTOR_ELT(alist, 0, avector);
	UNPROTECT(1);

       /* create the second vector and populate it */
        n = 4;
        PROTECT(avector = allocVector(INTSXP, n));
        INTEGER(avector)[0] = 5;
        INTEGER(avector)[1] = 9;
        INTEGER(avector)[2] = 2;
        INTEGER(avector)[3] = 7;
        /* stick it into the list */
        SET_VECTOR_ELT(alist, 1, avector);
        UNPROTECT(1);

	UNPROTECT(1);  /* avector*/
	return avector;

}


in R

dyn.load("pie.so")
.Call("pie")




Thomas Lumley			Assoc. Professor, Biostatistics
tlumley at u.washington.edu	University of Washington, Seattle




More information about the R-help mailing list