JF,
I would like to write your code directly in C / C ++ and include R in your program through
Using the above approach, you can create a package that mimics the functionality of python or simply wrap Python code inside an RCPP package directly. This last point is discussed in the next tutorial.
I hope that the explanation above and the sample code below will help you in the right direction.
Rcpp Code Example:
Listener.R
setwd("~/dev/stackoverflow/40896072") # install.packages("installr") # require(installr) # install.Rtools() # install.packages("Rcpp") # # Test and Verify # Rcpp::evalCpp("2+2") Rcpp::sourceCpp( file = "./listener.cc") listen()
Listener.cc
/* listener.c - a datagram socket 'server' * simply displays message received then dies! */ #include <stdio.h> #include <stdlib.h> #include <unistd.h> #include <errno.h> #include <string.h> #include <sys/types.h> #include <sys/socket.h> #include <netinet/in.h> #include <arpa/inet.h> #include <Rcpp.h> using namespace Rcpp; #define MYPORT 5555 /* the port users connect to */ #define MAXBUFLEN 100 // [[Rcpp::export]] int listen() { int sockfd; struct sockaddr_in my_addr; /* info for my addr ie server */ struct sockaddr_in their_addr; /* client address info */ socklen_t addr_len; ssize_t numbytes; char buf[ MAXBUFLEN]; printf( "Running\n"); if( (sockfd = socket( AF_INET, SOCK_DGRAM, 0)) == -1) { perror( "Listener socket"); exit( 1); } memset( &my_addr, 0, sizeof( my_addr)); /* zero struct */ my_addr.sin_family = AF_INET; /* host byte order ... */ my_addr.sin_port = htons( MYPORT); /* ... short, network byte order */ my_addr.sin_addr.s_addr = INADDR_ANY; /* any of server IP addrs */ if( bind( sockfd, (struct sockaddr *)&my_addr, sizeof( struct sockaddr)) == -1) { perror( "Listener bind"); exit( 1); } addr_len = sizeof( struct sockaddr); if( (numbytes = recvfrom( sockfd, buf, MAXBUFLEN - 1, 0, (struct sockaddr *) &their_addr, &addr_len)) == -1) { perror( "Listener recvfrom"); exit( 1); } printf( "Got packet from %s\n", inet_ntoa( their_addr.sin_addr)); printf( "Packet is %zd bytes long\n", numbytes); buf[ numbytes] = '\0'; /* end of string */ printf( "Packet contains \"%s\"\n", buf); close( sockfd); return 0; }
Client.R
setwd("~/dev/stackoverflow/40896072") # install.packages("installr") # require(installr) # install.Rtools() # install.packages("Rcpp") # # Test and Verify # Rcpp::evalCpp("2+2") Rcpp::sourceCpp( file = "./client.cc") client()
Client.cc
/* client.c - a datagram 'client' */ #include <stdio.h> #include <stdlib.h> #include <unistd.h> #include <errno.h> #include <string.h> #include <sys/types.h> #include <sys/socket.h> #include <netinet/in.h> #include <arpa/inet.h> #include <netdb.h> /* for gethostbyname() */ //#include <Rcpp.h> //using namespace Rcpp; #define PORT 5555 /* server port the client connects to */ // [[Rcpp::export]] int client() { socklen_t sockfd; ssize_t numbytes; struct hostent *he; struct sockaddr_in their_addr; /* server address info */ /* resolve server host name or IP address */ if ( (he = gethostbyname("localhost")) == NULL ) { perror( "Talker gethostbyname"); exit( 1); } if ( (sockfd = socket( AF_INET, SOCK_DGRAM, 0)) == -1) { perror( "Talker socket"); exit( 1); } memset( &their_addr,0, sizeof(their_addr) ); /* zero struct */ their_addr.sin_family = AF_INET; /* host byte order .. */ their_addr.sin_port = htons( PORT); /* .. short, netwk byte order */ their_addr.sin_addr = *( (struct in_addr *)he -> h_addr); if( (numbytes = sendto( sockfd, "Hello", strlen("Hello"), 0, (struct sockaddr *) &their_addr, sizeof( struct sockaddr))) == -1) { perror( "Talker sendto"); exit( 1); } printf( "Sent %zd bytes to %s\n", numbytes, inet_ntoa( their_addr.sin_addr)); close( sockfd ); return 0; }
Runtime output
