From 22437c8f41b28249a976b0b96545f3c35614933c Mon Sep 17 00:00:00 2001 From: Yashwant Date: Mon, 27 Jul 2020 10:34:48 +0530 Subject: [PATCH 01/11] Initial commit. --- CMake/GenerateGoBinding.cmake | 13 -- CMakeLists.txt | 12 +- README.md | 18 +- doc/guide/bindings.hpp | 8 +- doc/guide/cli_quickstart.hpp | 5 +- doc/guide/go_quickstart.hpp | 6 +- doc/guide/julia_quickstart.hpp | 5 +- doc/guide/r_quickstart.hpp | 189 ++++++++++++++++++ doc/tutorials/tutorials.txt | 1 + src/mlpack/bindings/R/CMakeLists.txt | 6 +- src/mlpack/bindings/R/default_param.hpp | 95 +++++++++ src/mlpack/bindings/R/default_param_impl.hpp | 145 ++++++++++++++ src/mlpack/bindings/R/get_printable_type.hpp | 120 +++++++++++ .../bindings/R/get_printable_type_impl.hpp | 161 +++++++++++++++ src/mlpack/bindings/R/print_doc_functions.hpp | 52 ++++- .../bindings/R/print_doc_functions_impl.hpp | 155 +++++++++++++- src/mlpack/bindings/R/print_type_doc.hpp | 86 ++++++++ src/mlpack/bindings/R/print_type_doc_impl.hpp | 164 +++++++++++++++ src/mlpack/bindings/R/r_method.cpp.in | 4 +- src/mlpack/bindings/go/CMakeLists.txt | 2 +- src/mlpack/bindings/julia/get_julia_type.hpp | 2 +- .../bindings/markdown/default_param.hpp | 6 + .../bindings/markdown/get_binding_name.cpp | 5 + .../bindings/markdown/get_printable_type.hpp | 6 + .../markdown/print_doc_functions_impl.hpp | 60 +++++- .../bindings/markdown/print_type_doc.hpp | 5 + src/mlpack/core/util/mlpack_main.hpp | 2 +- src/mlpack/methods/adaboost/CMakeLists.txt | 2 +- src/mlpack/methods/approx_kfn/CMakeLists.txt | 2 +- src/mlpack/methods/cf/CMakeLists.txt | 2 +- src/mlpack/methods/dbscan/CMakeLists.txt | 2 +- .../methods/decision_stump/CMakeLists.txt | 2 +- .../methods/decision_tree/CMakeLists.txt | 2 +- src/mlpack/methods/det/CMakeLists.txt | 2 +- src/mlpack/methods/emst/CMakeLists.txt | 2 +- src/mlpack/methods/fastmks/CMakeLists.txt | 2 +- src/mlpack/methods/gmm/CMakeLists.txt | 6 +- src/mlpack/methods/hmm/CMakeLists.txt | 8 +- .../methods/hoeffding_trees/CMakeLists.txt | 2 +- src/mlpack/methods/kde/CMakeLists.txt | 2 +- src/mlpack/methods/kernel_pca/CMakeLists.txt | 2 +- src/mlpack/methods/kmeans/CMakeLists.txt | 2 +- src/mlpack/methods/lars/CMakeLists.txt | 2 +- .../methods/linear_regression/CMakeLists.txt | 2 +- src/mlpack/methods/linear_svm/CMakeLists.txt | 2 +- src/mlpack/methods/lmnn/CMakeLists.txt | 2 +- .../local_coordinate_coding/CMakeLists.txt | 2 +- .../logistic_regression/CMakeLists.txt | 2 +- src/mlpack/methods/lsh/CMakeLists.txt | 2 +- src/mlpack/methods/mean_shift/CMakeLists.txt | 2 +- src/mlpack/methods/naive_bayes/CMakeLists.txt | 2 +- src/mlpack/methods/nca/CMakeLists.txt | 2 +- .../methods/neighbor_search/CMakeLists.txt | 4 +- src/mlpack/methods/nmf/CMakeLists.txt | 2 +- src/mlpack/methods/pca/CMakeLists.txt | 2 +- src/mlpack/methods/perceptron/CMakeLists.txt | 2 +- src/mlpack/methods/preprocess/CMakeLists.txt | 11 +- src/mlpack/methods/radical/CMakeLists.txt | 2 +- .../methods/random_forest/CMakeLists.txt | 2 +- .../methods/range_search/CMakeLists.txt | 2 +- src/mlpack/methods/rann/CMakeLists.txt | 2 +- .../methods/softmax_regression/CMakeLists.txt | 2 +- .../methods/sparse_coding/CMakeLists.txt | 2 +- 63 files changed, 1328 insertions(+), 98 deletions(-) delete mode 100644 CMake/GenerateGoBinding.cmake create mode 100644 doc/guide/r_quickstart.hpp create mode 100644 src/mlpack/bindings/R/default_param.hpp create mode 100644 src/mlpack/bindings/R/default_param_impl.hpp create mode 100644 src/mlpack/bindings/R/get_printable_type.hpp create mode 100644 src/mlpack/bindings/R/get_printable_type_impl.hpp create mode 100644 src/mlpack/bindings/R/print_type_doc.hpp create mode 100644 src/mlpack/bindings/R/print_type_doc_impl.hpp diff --git a/CMake/GenerateGoBinding.cmake b/CMake/GenerateGoBinding.cmake deleted file mode 100644 index e49bde96b2a..00000000000 --- a/CMake/GenerateGoBinding.cmake +++ /dev/null @@ -1,13 +0,0 @@ -# GenerateGoBinding.cmake: a CMake script that actually runs the given program to -# generate an mlpack binding file. -# -# This script depends on the following arguments: -# -# GENERATE_H_PROGRAM: the program to run to generate the .h file. -# H_OUTPUT_FILE: the file to store the output in. -# GENERATE_GO_PROGRAM: the program to run to generate the .go file. -# GO_OUTPUT_FILE: the file to store the output in. -# GENERATE_CPP_PROGRAM: the program to run to generate the .cpp file. -# CPP_OUTPUT_FILE: the file to store the output in. -execute_process(COMMAND ${GENERATE_BINDING_PROGRAM} - OUTPUT_FILE ${BINDING_OUTPUT_FILE}) diff --git a/CMakeLists.txt b/CMakeLists.txt index a74953bb583..95f1efd46e5 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -278,7 +278,13 @@ endif() # ENSMALLEN_INCLUDE_DIR - include directory for ensmallen # STB_IMAGE_INCLUDE_DIR - include directory for STB image library # MATHJAX_ROOT - root of MathJax installation -find_package(Armadillo 8.400.0 REQUIRED) + +# Set minimum library version required by mlpack. +set(ARMADILLO_VERSION "8.400.0") +set(ENSMALLEN_VERSION "2.10.0") +set(BOOST_VERSION "1.58") + +find_package(Armadillo "${ARMADILLO_VERSION}" REQUIRED) # Include directories for the previous dependencies. set(MLPACK_INCLUDE_DIRS ${MLPACK_INCLUDE_DIRS} ${ARMADILLO_INCLUDE_DIRS}) @@ -344,7 +350,7 @@ endif () # Find ensmallen. # Once ensmallen is readily available in package repos, the automatic downloader # here can be removed. -find_package(Ensmallen 2.10.0) +find_package(Ensmallen "${ENSMALLEN_VERSION}") if (NOT ENSMALLEN_FOUND) if (DOWNLOAD_ENSMALLEN) file(DOWNLOAD http://www.ensmallen.org/files/ensmallen-latest.tar.gz @@ -424,7 +430,7 @@ set(Boost_ADDITIONAL_VERSIONS # TODO for the brave: transition all mlpack's CMake to 'target-based modern # CMake'. Good luck! You'll need it. set(Boost_NO_BOOST_CMAKE 1) -find_package(Boost 1.58 +find_package(Boost "${BOOST_VERSION}" COMPONENTS unit_test_framework serialization diff --git a/README.md b/README.md index 8d164809f0b..94b3d668271 100644 --- a/README.md +++ b/README.md @@ -32,7 +32,7 @@ bindings to other languages. It is meant to be a machine learning analog to LAPACK, and aims to implement a wide array of machine learning methods and functions as a "swiss army knife" for machine learning researchers. In addition to its powerful C++ interface, mlpack also provides command-line programs, -Python bindings, and Julia bindings. +Python bindings, Julia bindings, Go bindings and R bindings. [//]: # (numfocus-fiscal-sponsor-attribution) @@ -121,6 +121,20 @@ following Python packages are installed: If you would like to build the Julia bindings, make sure that Julia >= 1.3.0 is installed. +If you would like to build the Go bindings, make sure that Go >= 1.11.0 is +installed with this package. + + gonum + +If you would like to build the R bindings, make sure that R >= 3.5 is +installed with these R packages. + + Rcpp >= 0.12.12 + RcppArmadillo >= 0.8.400.0 + RcppEnsmallen >= 0.2.10.0 + BH >= 1.58 + roxygen2 + If the STB library headers are available, image loading support will be compiled. @@ -190,6 +204,8 @@ Options are specified with the -D flag. The allowed options include: BUILD_GO_BINDINGS=(ON/OFF): whether or not to build Go bindings GO_EXECUTABLE=(/path/to/go): Path to specific Go executable BUILD_GO_SHLIB=(ON/OFF): whether or not to build shared libraries required by Go bindings + BUILD_R_BINDINGS=(ON/OFF): whether or not to build R bindings + R_EXECUTABLE=(/path/to/R): Path to specific R executable BUILD_TESTS=(ON/OFF): whether or not to build tests BUILD_SHARED_LIBS=(ON/OFF): compile shared libraries as opposed to static libraries diff --git a/doc/guide/bindings.hpp b/doc/guide/bindings.hpp index 96e57a01b75..13cb7ee12ed 100644 --- a/doc/guide/bindings.hpp +++ b/doc/guide/bindings.hpp @@ -147,8 +147,7 @@ PROGRAM_INFO("Mean Shift Clustering", "\n\n" "The output labels may be saved with the " + PRINT_PARAM_STRING("output") + " output parameter and the centroids of each cluster may be saved with the" - " " + PRINT_PARAM_STRING("centroid") + " output parameter." - "\n\n" + " " + PRINT_PARAM_STRING("centroid") + " output parameter.", "For example, to run mean shift clustering on the dataset " + PRINT_DATASET("data") + " and store the centroids to " + PRINT_DATASET("centroids") + ", the following command may be used: " @@ -286,7 +285,7 @@ is of the form @code PROGRAM_INFO("program name", "short documentation", "long documentation", - SEE_ALSO("link", "description"), ...) + "examples", SEE_ALSO("link", "description"), ...) @endcode The short documentation should be two sentences indicating what the program @@ -425,8 +424,7 @@ Input C++ (full program, 'random_numbers_main.cpp'): "The output random numbers can be saved with the " + PRINT_PARAM_STRING("output") + " output parameter. In addition, a " "randomly generated linear regression model can be saved with the " + - PRINT_PARAM_STRING("output_model") + " output parameter." - "\n\n" + PRINT_PARAM_STRING("output_model") + " output parameter.", "For example, to generate 100 random numbers with 3 subtracted from them " "and save the output to " + PRINT_DATASET("rand") + " and the random " "model to " + PRINT_MODEL("rand_lr") + ", use the following " diff --git a/doc/guide/cli_quickstart.hpp b/doc/guide/cli_quickstart.hpp index e084abba5f1..22d91c49cae 100644 --- a/doc/guide/cli_quickstart.hpp +++ b/doc/guide/cli_quickstart.hpp @@ -10,8 +10,9 @@ This page describes how you can quickly get started using mlpack from the command-line and gives a few examples of usage, and pointers to deeper documentation. -This quickstart guide is also available for @ref python_quickstart "Python" and -@ref julia_quickstart "Julia". +This quickstart guide is also available for @ref python_quickstart "Python" +@ref r_quickstart "R", @ref julia_quickstart "Julia" and +@ref go_quickstart "Go". @section cli_quickstart_install Installing mlpack diff --git a/doc/guide/go_quickstart.hpp b/doc/guide/go_quickstart.hpp index b476d1d85d9..4815a974bba 100644 --- a/doc/guide/go_quickstart.hpp +++ b/doc/guide/go_quickstart.hpp @@ -9,9 +9,9 @@ This page describes how you can quickly get started using mlpack from Go and gives a few examples of usage, and pointers to deeper documentation. -This quickstart guide is also available for -@ref cli_quickstart "the command-line", @ref python_quickstart "Python" -and @ref julia_quickstart "Julia". +This quickstart guide is also available for @ref python_quickstart "Python" +@ref cli_quickstart "the command-line", @ref julia_quickstart "Julia" and +@ref r_quickstart "R". @section go_quickstart_install Installing mlpack diff --git a/doc/guide/julia_quickstart.hpp b/doc/guide/julia_quickstart.hpp index a63c86e7e1a..e45820af52c 100644 --- a/doc/guide/julia_quickstart.hpp +++ b/doc/guide/julia_quickstart.hpp @@ -9,8 +9,9 @@ This page describes how you can quickly get started using mlpack from Julia and gives a few examples of usage, and pointers to deeper documentation. -This quickstart guide is also available for -@ref cli_quickstart "the command-line" and @ref python_quickstart "Python". +This quickstart guide is also available for @ref python_quickstart "Python" +@ref cli_quickstart "the command-line", @ref go_quickstart "Go" and +@ref r_quickstart "R". @section julia_quickstart_install Installing mlpack diff --git a/doc/guide/r_quickstart.hpp b/doc/guide/r_quickstart.hpp new file mode 100644 index 00000000000..20c44df1217 --- /dev/null +++ b/doc/guide/r_quickstart.hpp @@ -0,0 +1,189 @@ +/** + * @file r_quickstart.hpp + * @author Yashwant Singh Parihar + +@page r_quickstart mlpack in R quickstart guide + +@section r_quickstart_intro Introduction + +This page describes how you can quickly get started using mlpack from R and +gives a few examples of usage, and pointers to deeper documentation. + +This quickstart guide is also available for @ref python_quickstart "Python" +@ref cli_quickstart "the command-line", @ref julia_quickstart "Julia" and +@ref go_quickstart "Go". + +@section r_quickstart_install Installing mlpack + +Installing the mlpack bindings for R is straightforward; you can just use +cran mirror: + +@code{.R} +install.packages('mlpack') +@endcode + +Building the R bindings from scratch is a little more in-depth, though. For +information on that, follow the instructions on the @ref build page, and be sure +to specify @c -DBUILD_R_BINDINGS=ON to CMake; you may need to also set the +location of the R program with @c -DR_EXECUTABLE=/path/to/R. + +@section r_quickstart_example Simple mlpack quickstart example + +As a really simple example of how to use mlpack from R, let's do some +simple classification on a subset of the standard machine learning @c covertype +dataset. We'll first split the dataset into a training set and a testing set, +then we'll train an mlpack random forest on the training data, and finally we'll +print the accuracy of the random forest on the test dataset. + +You can copy-paste this code directly into R to run it. + +@code{.R} +suppressMessages({ + library("mlpack") + library("data.table") +}) + +# Load the dataset from an online URL. Replace with 'covertype.csv.gz' if you +# want to use on the full dataset. +df <- fread("https://www.mlpack.org/datasets/covertype-small.csv.gz") + +# Split the labels. +labels <- df[, .(label)] +dataset <- df[, label:=NULL] + +# Split the dataset using mlpack. +prepdata <- preprocess_split(input = dataset, + input_labels = labels, + test_ratio = 0.3, + verbose = TRUE) + +# Train a random forest. +output <- random_forest(training = prepdata$training, + labels = prepdata$training_labels, + print_training_accuracy = TRUE, + num_trees = 10, + minimum_leaf_size = 3, + verbose = TRUE) +rf_model <- output$output_model + +# Predict the labels of the test points. +output <- random_forest(input_model = rf_model, + test = prepdata$test, + verbose = TRUE) + +# Now print the accuracy. The third return value ('probabilities'), which we +# ignored here, could also be used to generate an ROC curve. +correct <- sum(output$predictions == prepdata$test_labels) +cat(correct, "out of", length(prepdata$test_labels), "test points correct", + correct / length(prepdata$test_labels) * 100.0, "%\n") +@endcode + +We can see that we achieve reasonably good accuracy on the test dataset (80%+); +if we use the full @c covertype.csv.gz, the accuracy should increase +significantly (but training will take longer). + +It's easy to modify the code above to do more complex things, or to use +different mlpack learners, or to interface with other machine learning toolkits. + +@section r_quickstart_whatelse What else does mlpack implement? + +The example above has only shown a little bit of the functionality of mlpack. +Lots of other commands are available with different functionality. A full list +of each of these commands and full documentation can be found on the following +page: + + - r documentation + +For more information on what mlpack does, see https://www.mlpack.org/. +Next, let's go through another example for providing movie recommendations with +mlpack. + +@section r_quickstart_movierecs Using mlpack for movie recommendations + +In this example, we'll train a collaborative filtering model using mlpack's +cf() method. We'll train this on the MovieLens dataset from +https://grouplens.org/datasets/movielens/, and then we'll use the model that we +train to give recommendations. + +You can copy-paste this code directly into R to run it. + +@code{.R} +suppressMessages({ + library("mlpack") + library("data.table") +}) + +# First, load the MovieLens dataset. This is taken from files.grouplens.org/ +# but reposted on mlpack.org as unpacked and slightly preprocessed data. +ratings <- fread("http://www.mlpack.org/datasets/ml-20m/ratings-only.csv.gz") +movies <- fread("http://www.mlpack.org/datasets/ml-20m/movies.csv.gz") + +# Hold out 10% of the dataset into a test set so we can evaluate performance. +predata <- preprocess_split(input = ratings, + test_ratio = 0.1, + verbose = TRUE) + +# Train the model. Change the rank to increase/decrease the complexity of the +# model. +output <- cf(training = predata$training, + test = predata$test, + rank = 10, + verbose = TRUE, + max_iteration=2, + algorithm = "RegSVD") +cf_model <- output$output_model + +# Now query the 5 top movies for user 1. +output <- cf(input_model = cf_model, + query = matrix(1), + recommendations = 10, + verbose = TRUE) + +# Get the names of the movies for user 1. +cat("Recommendations for user 1:\n") +for (i in 1:10) { + cat(" ", i, ":", as.character(movies[output$output[i], 3]), "\n") +} +@endcode + +Here is some example output, showing that user 1 seems to have good taste in +movies: + +@code{.unparsed} +Recommendations for user 1: + 0: Casablanca (1942) + 1: Pan's Labyrinth (Laberinto del fauno, El) (2006) + 2: Godfather, The (1972) + 3: Answer This! (2010) + 4: Life Is Beautiful (La Vita รจ bella) (1997) + 5: Adventures of Tintin, The (2011) + 6: Dark Knight, The (2008) + 7: Out for Justice (1991) + 8: Dr. Strangelove or: How I Learned to Stop Worrying and Love the Bomb (1964) + 9: Schindler's List (1993) +@endcode + +@section r_quickstart_nextsteps Next steps with mlpack + +Now that you have done some simple work with mlpack, you have seen how it can +easily plug into a data science workflow in R. A great thing to do next +would be to look at more documentation for the R mlpack bindings: + + - R mlpack + binding documentation + +Also, mlpack is much more flexible from C++ and allows much greater +functionality. So, more complicated tasks are possible if you are willing to +write C++ (or perhaps Rcpp). To get started learning about mlpack in C++, the +following resources might be helpful: + + - mlpack + C++ tutorials + - mlpack + build and installation guide + - Simple + sample C++ mlpack programs + - mlpack + Doxygen documentation homepage + + */ diff --git a/doc/tutorials/tutorials.txt b/doc/tutorials/tutorials.txt index 5882217618b..6f6bb7356d9 100644 --- a/doc/tutorials/tutorials.txt +++ b/doc/tutorials/tutorials.txt @@ -15,6 +15,7 @@ get started with mlpack in different languages. - \ref cli_quickstart - \ref julia_quickstart - \ref go_quickstart + - \ref r_quickstart @section introd_tut Introductory Tutorials diff --git a/src/mlpack/bindings/R/CMakeLists.txt b/src/mlpack/bindings/R/CMakeLists.txt index 6f7c3d21c12..a77c5112f64 100644 --- a/src/mlpack/bindings/R/CMakeLists.txt +++ b/src/mlpack/bindings/R/CMakeLists.txt @@ -19,9 +19,9 @@ if (BUILD_R_BINDINGS) include(${CMAKE_SOURCE_DIR}/CMake/FindRModule.cmake) # If mlpack upgrade the version of dependencies, then we also have to update the version here. - set(RcppArmadillo_Version "0.8.400.0.0") - set(RcppEnsmallen_Version "0.2.10.0") - set(BH_Version "1.58.0") + set(RcppArmadillo_Version "0.${ARMADILLO_VERSION}") + set(RcppEnsmallen_Version "0.${ENSMALLEN_VERSION}") + set(BH_Version "${BOOST_VERSION}") ## We need to check here if R is even available. Although actually ## technically, I'm not sure if we even need to know! For the tests though we diff --git a/src/mlpack/bindings/R/default_param.hpp b/src/mlpack/bindings/R/default_param.hpp new file mode 100644 index 00000000000..22942bf2127 --- /dev/null +++ b/src/mlpack/bindings/R/default_param.hpp @@ -0,0 +1,95 @@ +/** + * @file bindings/r/default_param.hpp + * @author Yashwant Singh Parihar + * + * Return the default value of a parameter, depending on its type. + * + * mlpack is free software; you may redistribute it and/or modify it under the + * terms of the 3-clause BSD license. You should have received a copy of the + * 3-clause BSD license along with mlpack. If not, see + * http://www.opensource.org/licenses/BSD-3-Clause for more information. + */ +#ifndef MLPACK_BINDINGS_R_DEFAULT_PARAM_HPP +#define MLPACK_BINDINGS_R_DEFAULT_PARAM_HPP + +#include +#include +#include + +namespace mlpack { +namespace bindings { +namespace r { + +/** + * Return the default value of an option. This is for regular types. + */ +template +std::string DefaultParamImpl( + util::ParamData& data, + const typename boost::disable_if>::type* = 0, + const typename boost::disable_if>::type* = 0, + const typename boost::disable_if>::type* = 0, + const typename boost::disable_if>::type* = 0, + const typename boost::disable_if>>::type* = 0); + +/** + * Return the default value of a vector option. + */ +template +std::string DefaultParamImpl( + util::ParamData& data, + const typename boost::enable_if>::type* = 0); + +/** + * Return the default value of a string option. + */ +template +std::string DefaultParamImpl( + util::ParamData& data, + const typename boost::enable_if>::type* = 0); + +/** + * Return the default value of a matrix option, a tuple option, a + * serializable option, or a string option (this returns the default filename, + * or '' if the default is no file). + */ +template +std::string DefaultParamImpl( + util::ParamData& data, + const typename boost::enable_if_c< + arma::is_arma_type::value || + std::is_same>::value>::type* /* junk */ = 0); + +/** + * Return the default value of a model option (this returns the default + * filename, or '' if the default is no file). + */ +template +std::string DefaultParamImpl( + util::ParamData& data, + const typename boost::disable_if>::type* = 0, + const typename boost::enable_if>::type* = 0); + +/** + * Return the default value of an option. This is the function that will be + * placed into the IO functionMap. + */ +template +void DefaultParam(util::ParamData& data, + const void* /* input */, + void* output) +{ + std::string* outstr = (std::string*) output; + *outstr = DefaultParamImpl::type>(data); +} + +} // namespace r +} // namespace bindings +} // namespace mlpack + +// Include implementation. +#include "default_param_impl.hpp" + +#endif diff --git a/src/mlpack/bindings/R/default_param_impl.hpp b/src/mlpack/bindings/R/default_param_impl.hpp new file mode 100644 index 00000000000..69b379de805 --- /dev/null +++ b/src/mlpack/bindings/R/default_param_impl.hpp @@ -0,0 +1,145 @@ +/** + * @file bindings/R/default_param_impl.hpp + * @author Yashwant Singh Parihar + * + * Return the default value of a parameter, depending on its type. + * + * mlpack is free software; you may redistribute it and/or modify it under the + * terms of the 3-clause BSD license. You should have received a copy of the + * 3-clause BSD license along with mlpack. If not, see + * http://www.opensource.org/licenses/BSD-3-Clause for more information. + */ +#ifndef MLPACK_BINDINGS_R_DEFAULT_PARAM_IMPL_HPP +#define MLPACK_BINDINGS_R_DEFAULT_PARAM_IMPL_HPP + +#include "default_param.hpp" + +namespace mlpack { +namespace bindings { +namespace r { + +/** + * Return the default value of an option. + */ +template +std::string DefaultParamImpl( + util::ParamData& data, + const typename boost::disable_if>::type* /* junk */, + const typename boost::disable_if>::type* /* junk */, + const typename boost::disable_if>::type* /* junk */, + const typename boost::disable_if>::type*, + const typename boost::disable_if>>::type* /* junk */) +{ + std::ostringstream oss; + if (std::is_same::value) + oss << "FALSE"; + else + oss << boost::any_cast(data.value); + + return oss.str(); +} + +/** + * Return the default value of a vector option. + */ +template +std::string DefaultParamImpl( + util::ParamData& data, + const typename boost::enable_if>::type* /* junk */) +{ + // Print each element in an array delimited by square brackets. + std::ostringstream oss; + const T& vector = boost::any_cast(data.value); + oss << "c("; + if (std::is_same>::value) + { + if (vector.size() > 0) + { + for (size_t i = 0; i < vector.size() - 1; ++i) + { + oss << "'" << vector[i] << "', "; + } + + oss << "'" << vector[vector.size() - 1] << "'"; + } + + oss << ")"; + } + else + { + if (vector.size() > 0) + { + for (size_t i = 0; i < vector.size() - 1; ++i) + { + oss << vector[i] << ", "; + } + + oss << vector[vector.size() - 1]; + } + + oss << ")"; + } + return oss.str(); +} + +/** + * Return the default value of a string option. + */ +template +std::string DefaultParamImpl( + util::ParamData& data, + const typename boost::enable_if>::type*) +{ + const std::string& s = *boost::any_cast(&data.value); + return "\"" + s + "\""; +} + +/** + * Return the default value of a matrix option (this returns the default + * filename, or '' if the default is no file). + */ +template +std::string DefaultParamImpl( + util::ParamData& /* data */, + const typename boost::enable_if_c< + arma::is_arma_type::value || + std::is_same>::value>::type* /* junk */) +{ + // Get the filename and return it, or return an empty string. + if (std::is_same::value || + std::is_same::value || + std::is_same::value) + { + return "matrix()"; + } + else if (std::is_same>::value || + std::is_same>::value || + std::is_same>::value) + { + return "matrix(as.integer())"; + } + else + { + return "matrix()"; + } +} + +/** + * Return the default value of a model option (always "None"). + */ +template +std::string DefaultParamImpl( + util::ParamData& /* data */, + const typename boost::disable_if>::type* /* junk */, + const typename boost::enable_if>::type* /* junk */) +{ + return "NA"; +} + +} // namespace r +} // namespace bindings +} // namespace mlpack + +#endif diff --git a/src/mlpack/bindings/R/get_printable_type.hpp b/src/mlpack/bindings/R/get_printable_type.hpp new file mode 100644 index 00000000000..730422cade3 --- /dev/null +++ b/src/mlpack/bindings/R/get_printable_type.hpp @@ -0,0 +1,120 @@ +/** + * @file bindings/R/get_printable_type.hpp + * @author Yashwant Singh Parihar + * + * Template metaprogramming to return the string representation of the R + * type for a given R binding parameter. + * + * mlpack is free software; you may redistribute it and/or modify it under the + * terms of the 3-clause BSD license. You should have received a copy of the + * 3-clause BSD license along with mlpack. If not, see + * http://www.opensource.org/licenses/BSD-3-Clause for more information. + */ +#ifndef MLPACK_BINDINGS_R_GET_PRINTABLE_TYPE_HPP +#define MLPACK_BINDINGS_R_GET_PRINTABLE_TYPE_HPP + +#include +#include + +namespace mlpack { +namespace bindings { +namespace r { + +template +inline std::string GetPrintableType( + util::ParamData& /* d */, + const typename boost::disable_if>::type* = 0, + const typename boost::disable_if>::type* = 0, + const typename boost::disable_if>::type* = 0, + const typename boost::disable_if>>::type* = 0); + +template<> +inline std::string GetPrintableType( + util::ParamData& /* d */, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>>::type*); + +template<> +inline std::string GetPrintableType( + util::ParamData& /* d */, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>>::type*); + +template<> +inline std::string GetPrintableType( + util::ParamData& /* d */, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>>::type*); + +template<> +inline std::string GetPrintableType( + util::ParamData& /* d */, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>>::type*); + +template<> +inline std::string GetPrintableType( + util::ParamData& /* d */, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>>::type*); + +template +inline std::string GetPrintableType( + util::ParamData& d, + const typename boost::enable_if>::type* = 0, + const typename boost::disable_if>>::type* = 0); + +template +inline std::string GetPrintableType( + util::ParamData& /* d */, + const typename boost::enable_if>::type* = 0, + const typename boost::disable_if>>::type* = 0); + +template +inline std::string GetPrintableType( + util::ParamData& /* d */, + const typename boost::enable_if>>::type* = 0); + +template +inline std::string GetPrintableType( + util::ParamData& d, + const typename boost::disable_if>::type* = 0, + const typename boost::enable_if>::type* = 0, + const typename boost::disable_if>>::type* = 0); + +template +void GetPrintableType(util::ParamData& d, + const void* /* input */, + void* output) +{ + *((std::string*) output) = + GetPrintableType::type>(d); +} + +} // namespace r +} // namespace bindings +} // namespace mlpack + +#include "get_printable_type_impl.hpp" + +#endif diff --git a/src/mlpack/bindings/R/get_printable_type_impl.hpp b/src/mlpack/bindings/R/get_printable_type_impl.hpp new file mode 100644 index 00000000000..cedecdf2ab3 --- /dev/null +++ b/src/mlpack/bindings/R/get_printable_type_impl.hpp @@ -0,0 +1,161 @@ +/** + * @file bindings/R/get_printable_type_impl.hpp + * @author Yashwant Singh Parihar + * + * Template metaprogramming to return the string representation of the R + * type for a given R binding parameter. + * + * mlpack is free software; you may redistribute it and/or modify it under the + * terms of the 3-clause BSD license. You should have received a copy of the + * 3-clause BSD license along with mlpack. If not, see + * http://www.opensource.org/licenses/BSD-3-Clause for more information. + */ +#ifndef MLPACK_BINDINGS_R_GET_PRINTABLE_TYPE_IMPL_HPP +#define MLPACK_BINDINGS_R_GET_PRINTABLE_TYPE_IMPL_HPP + +#include "get_printable_type.hpp" + +namespace mlpack { +namespace bindings { +namespace r { + +template +inline std::string GetPrintableType( + util::ParamData& /* d */, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>>::type*) +{ + return "unknown"; +} + +template<> +inline std::string GetPrintableType( + util::ParamData& /* d */, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>>::type*) +{ + return "integer"; +} + +template<> +inline std::string GetPrintableType( + util::ParamData& /* d */, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>>::type*) +{ + return "numeric"; +} + +template<> +inline std::string GetPrintableType( + util::ParamData& /* d */, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>>::type*) +{ + return "character"; +} + +template<> +inline std::string GetPrintableType( + util::ParamData& /* d */, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>>::type*) +{ + return "integer"; +} + +template<> +inline std::string GetPrintableType( + util::ParamData& /* d */, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>>::type*) +{ + return "logical"; +} + +template +inline std::string GetPrintableType( + util::ParamData& d, + const typename boost::enable_if>::type*, + const typename boost::disable_if>>::type*) +{ + return "vector of " + GetPrintableType(d) + "s"; +} + +template +inline std::string GetPrintableType( + util::ParamData& /* d */, + const typename boost::enable_if>::type*, + const typename boost::disable_if>>::type*) +{ + std::string type = "numeric matrix"; + if (std::is_same::value) + { + if (T::is_row || T::is_col) + type = "numeric vector"; + } + else if (std::is_same::value) + { + type = "integer matrix"; + if (T::is_row || T::is_col) + type = "integer vector"; + } + + return type; +} + +template +inline std::string GetPrintableType( + util::ParamData& /* d */, + const typename boost::enable_if>>::type*) +{ + return "categorical matrix/data.frame"; +} + +template +inline std::string GetPrintableType( + util::ParamData& d, + const typename boost::disable_if>::type*, + const typename boost::enable_if>::type*, + const typename boost::disable_if>>::type*) +{ + std::string type = util::StripType(d.cppType); + if (type == "mlpackModel") + { + // If this is true, then we are being called from the Markdown bindings. + // This will be printed as the general documentation for model types. + return " (mlpack model)"; + } + else + { + return type; + } +} + +} // namespace r +} // namespace bindings +} // namespace mlpack + +#endif diff --git a/src/mlpack/bindings/R/print_doc_functions.hpp b/src/mlpack/bindings/R/print_doc_functions.hpp index e4026c920ab..27fafff169c 100644 --- a/src/mlpack/bindings/R/print_doc_functions.hpp +++ b/src/mlpack/bindings/R/print_doc_functions.hpp @@ -19,17 +19,46 @@ namespace mlpack { namespace bindings { namespace r { +/** + * Given the name of a binding, print its R name. + */ +inline std::string GetBindingName(const std::string& bindingName); + +/** + * Print any import information for the R binding. + */ +inline std::string PrintImport(); + +/** + * Print any special information about input options. + */ +inline std::string PrintInputOptionInfo(); + +/** + * Print any special information about output options. + */ +inline std::string PrintOutputOptionInfo(); + /** * Given a parameter type, print the corresponding value. */ template inline std::string PrintValue(const T& value, bool quotes); -// Special overload for booleans. +/** + * Special overload for booleans. + */ template<> inline std::string PrintValue(const bool& value, bool quotes); -// Recursion base case. +/** + * Given a parameter name, print its corresponding default value. + */ +inline std::string PrintDefault(const std::string& paramName); + +/** + * Recursion base case. + */ inline std::string PrintInputOptions(); /** @@ -41,11 +70,14 @@ std::string PrintInputOptions(const std::string& paramName, const T& value, Args... args); -// Recursion base case. -inline std::string PrintOutputOptions(); +/** + * Recursion base case. + */ +inline std::string PrintOutputOptions(const bool /* markdown */); template -std::string PrintOutputOptions(const std::string& paramName, +std::string PrintOutputOptions(const bool markdown, + const std::string& paramName, const T& value, Args... args); @@ -54,7 +86,15 @@ std::string PrintOutputOptions(const std::string& paramName, * contents), print the corresponding function call. */ template -std::string ProgramCall(const std::string& programName, Args... args); +std::string ProgramCall(const bool markdown, + const std::string& programName, + Args... args); + +/** + * Given the name of a binding, print a program call assuming that all options + * are specified. + */ +inline std::string ProgramCall(const std::string& programName); /** * Given the name of a model, print it. Here we do not need to modify anything. diff --git a/src/mlpack/bindings/R/print_doc_functions_impl.hpp b/src/mlpack/bindings/R/print_doc_functions_impl.hpp index e192ee833b2..47705c6f285 100644 --- a/src/mlpack/bindings/R/print_doc_functions_impl.hpp +++ b/src/mlpack/bindings/R/print_doc_functions_impl.hpp @@ -19,6 +19,40 @@ namespace mlpack { namespace bindings { namespace r { +/** + * Given the name of a binding, print its R name. + */ +inline std::string GetBindingName(const std::string& bindingName) +{ + // No modification is needed to the name---we just use it as-is. + return bindingName + "()"; +} + +/** + * Print any import information for the R binding. + */ +inline std::string PrintImport() +{ + return "library(mlpack)"; +} + +/** + * Print any special information about input options. + */ +inline std::string PrintInputOptionInfo() +{ + return ""; +} + +/** + * Print any special information about output options. + */ +inline std::string PrintOutputOptionInfo() +{ + return "Results are returned in a R list. The keys of the " + "list are the names of the output parameters."; +} + /** * Given a parameter type, print the corresponding value. */ @@ -34,7 +68,26 @@ inline std::string PrintValue(const T& value, bool quotes) return oss.str(); } -// Special overload for booleans. +/** + * Given a parameter name, print its corresponding default value. + */ +inline std::string PrintDefault(const std::string& paramName) +{ + if (IO::Parameters().count(paramName) == 0) + throw std::invalid_argument("unknown parameter " + paramName + "!"); + + util::ParamData& d = IO::Parameters()[paramName]; + + std::string defaultValue; + IO::GetSingleton().functionMap[d.tname]["DefaultParam"](d, NULL, + (void*) &defaultValue); + + return defaultValue; +} + +/** + * Special overload for booleans. + */ template<> inline std::string PrintValue(const bool& value, bool quotes) { @@ -48,7 +101,9 @@ inline std::string PrintValue(const bool& value, bool quotes) return "FALSE"; } -// Recursion base case. +/** + * Recursion base case. + */ std::string PrintInputOptions() { return ""; } /** @@ -92,11 +147,14 @@ std::string PrintInputOptions(const std::string& paramName, return result; } -// Recursion base case. -inline std::string PrintOutputOptions() { return ""; } +/** + * Recursion base case. + */ +inline std::string PrintOutputOptions(const bool /* markdown */) { return ""; } template -std::string PrintOutputOptions(const std::string& paramName, +std::string PrintOutputOptions(const bool markdown, + const std::string& paramName, const T& value, Args... args) { @@ -109,6 +167,8 @@ std::string PrintOutputOptions(const std::string& paramName, { // Print a new line for the output option. std::ostringstream oss; + if (markdown) + oss << "R> "; oss << value << " <- output$" << paramName; result = oss.str(); } @@ -122,7 +182,7 @@ std::string PrintOutputOptions(const std::string& paramName, } // Continue recursion. - std::string rest = PrintOutputOptions(args...); + std::string rest = PrintOutputOptions(markdown, args...); if (rest != "" && result != "") result += "\n"; result += rest; @@ -136,9 +196,13 @@ std::string PrintOutputOptions(const std::string& paramName, * contents), print the corresponding function call. */ template -std::string ProgramCall(const std::string& programName, Args... args) +std::string ProgramCall(const bool markdown, + const std::string& programName, + Args... args) { std::ostringstream oss; + if (markdown) + oss << "R> "; // Find out if we have any output options first. std::ostringstream ossOutput; @@ -153,7 +217,15 @@ std::string ProgramCall(const std::string& programName, Args... args) oss.str(""); // Reset it. // Now process each output option. - oss << PrintOutputOptions(args...); + oss << PrintOutputOptions(markdown, args...); + if (markdown) + { + if (oss.str() == "") + return util::HyphenateString(call, 2); + else + return util::HyphenateString(call, 2) + "\n" + oss.str(); + } + if (oss.str() == "") return "\\donttest{\n" + util::HyphenateString(call, 2) + "\n}"; else @@ -161,6 +233,73 @@ std::string ProgramCall(const std::string& programName, Args... args) "\n}"; } +/** + * Given the name of a binding, print a program call assuming that all options + * are specified. The programName should not be the output of GetBindingName(). + */ +inline std::string ProgramCall(const std::string& programName) +{ + std::ostringstream oss; + oss << "R> "; + + // Determine if we have any output options. + std::map& parameters = IO::Parameters(); + bool hasOutput = false; + for (auto it = parameters.begin(); it != parameters.end(); ++it) + { + if (!it->second.input) + { + hasOutput = true; + break; + } + } + + if (hasOutput) + oss << "d <- "; + + oss << programName << "("; + + // Now iterate over every input option. + bool first = true; + for (auto it = parameters.begin(); it != parameters.end(); ++it) + { + if (!it->second.input || (it->second.persistent && + it->second.name != "verbose")) + continue; + + if (!first) + oss << ", "; + else + first = false; + + // Print the input option. + oss << it->second.name << "="; + + std::string value; + IO::GetSingleton().functionMap[it->second.tname]["DefaultParam"]( + it->second, NULL, (void*) &value); + oss << value; + } + oss << ")"; + + std::string result = util::HyphenateString(oss.str(), 8); + + oss.str(""); + oss << result; + + // Now print output lines. + for (auto it = parameters.begin(); it != parameters.end(); ++it) + { + if (it->second.input) + continue; + + // Print a new line for the output option. + oss << std::endl << "R> " << it->second.name << " <- d$" << it->second.name; + } + + return oss.str(); +} + /** * Given the name of a model, print it. Here we do not need to modify anything. */ diff --git a/src/mlpack/bindings/R/print_type_doc.hpp b/src/mlpack/bindings/R/print_type_doc.hpp new file mode 100644 index 00000000000..c6b37ce1e40 --- /dev/null +++ b/src/mlpack/bindings/R/print_type_doc.hpp @@ -0,0 +1,86 @@ +/** + * @file bindings/R/print_type_doc.hpp + * @author Yashwant Singh Parihar + * + * Print documentation for a given type, detailing what the type actually is to + * the user. + * + * mlpack is free software; you may redistribute it and/or modify it under the + * terms of the 3-clause BSD license. You should have received a copy of the + * 3-clause BSD license along with mlpack. If not, see + * http://www.opensource.org/licenses/BSD-3-Clause for more information. + */ +#ifndef MLPACK_BINDINGS_R_PRINT_TYPE_DOC_HPP +#define MLPACK_BINDINGS_R_PRINT_TYPE_DOC_HPP + +#include + +namespace mlpack { +namespace bindings { +namespace r { + +/** + * Return a string representing the command-line type of an option. + */ +template +std::string PrintTypeDoc( + util::ParamData& data, + const typename boost::disable_if>::type* = 0, + const typename boost::disable_if>::type* = 0, + const typename boost::disable_if>::type* = 0, + const typename boost::disable_if>>::type* = 0); + +/** + * Return a string representing the command-line type of a vector. + */ +template +std::string PrintTypeDoc( + util::ParamData& data, + const typename std::enable_if::value>::type* = 0); + +/** + * Return a string representing the command-line type of a matrix option. + */ +template +std::string PrintTypeDoc( + util::ParamData& data, + const typename std::enable_if::value>::type* = 0); + +/** + * Return a string representing the command-line type of a matrix tuple option. + */ +template +std::string PrintTypeDoc( + util::ParamData& data, + const typename std::enable_if>::value>::type* = 0); + +/** + * Return a string representing the command-line type of a model. + */ +template +std::string PrintTypeDoc( + util::ParamData& data, + const typename boost::disable_if>::type* = 0, + const typename boost::enable_if>::type* = 0); + +/** + * Print the command-line type of an option into a string. + */ +template +void PrintTypeDoc(util::ParamData& data, + const void* /* input */, + void* output) +{ + *((std::string*) output) = + PrintTypeDoc::type>(data); +} + +} // namespace r +} // namespace bindings +} // namespace mlpack + +#include "print_type_doc_impl.hpp" + +#endif diff --git a/src/mlpack/bindings/R/print_type_doc_impl.hpp b/src/mlpack/bindings/R/print_type_doc_impl.hpp new file mode 100644 index 00000000000..878bfb836a5 --- /dev/null +++ b/src/mlpack/bindings/R/print_type_doc_impl.hpp @@ -0,0 +1,164 @@ +/** + * @file bindings/R/print_type_doc_impl.hpp + * @author Yashwant Singh Parihar + * + * Print documentation for a given type. + * + * mlpack is free software; you may redistribute it and/or modify it under the + * terms of the 3-clause BSD license. You should have received a copy of the + * 3-clause BSD license along with mlpack. If not, see + * http://www.opensource.org/licenses/BSD-3-Clause for more information. + */ +#ifndef MLPACK_BINDINGS_R_PRINT_TYPE_DOC_IMPL_HPP +#define MLPACK_BINDINGS_R_PRINT_TYPE_DOC_IMPL_HPP + +#include "print_type_doc.hpp" + +namespace mlpack { +namespace bindings { +namespace r { + +/** + * Return a string representing the command-line type of an option. + */ +template +std::string PrintTypeDoc( + util::ParamData& data, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>::type*, + const typename boost::disable_if>>::type*) +{ + // A flag type. + if (std::is_same::value) + { + return "A boolean flag option (TRUE or FALSE)."; + } + // An integer. + else if (std::is_same::value) + { + return "An integer (i.e., \"1\")."; + } + // A floating point value. + else if (std::is_same::value) + { + return "A floating-point number (i.e., \"0.5\")."; + } + // A string. + else if (std::is_same::value) + { + return "A character string (i.e., \"hello\")."; + } + // Not sure what it is... + else + { + throw std::invalid_argument("unknown parameter type " + data.cppType); + } +} + +/** + * Return a string representing the command-line type of a vector. + */ +template +std::string PrintTypeDoc( + util::ParamData& data, + const typename std::enable_if::value>::type*) +{ + if (std::is_same>::value) + { + return "A vector of integers; i.e., c(0, 1, 2)."; + } + else if (std::is_same>::value) + { + return "A vector of strings; i.e., c(\"hello\", \"goodbye\")."; + } + else + { + throw std::invalid_argument("unknown vector type " + data.cppType); + } +} + +/** + * Return a string representing the command-line type of a matrix option. + */ +template +std::string PrintTypeDoc( + util::ParamData& data, + const typename std::enable_if::value>::type*) +{ + if (std::is_same::value) + { + if (T::is_col || T::is_row) + { + return "A 1-d matrix-like containing 'numeric' data (could be an " + "'matrix' or 'data.frame' with one dimension of size 1)."; + } + else + { + return "A 2-d matrix-like containing 'numeric' data (could be an " + "'matrix' or a 'data.frame' or anything convertible to an " + "2-d 'matrix'."; + } + } + else if (std::is_same::value) + { + if (T::is_col || T::is_row) + { + return "A 1-d matrix-like containing 'integer' data (could be an " + "'matrix' or 'data.frame' with one dimension of size 1)."; + } + else + { + return "A 2-d matrix-like containing 'integer' data (could be an " + "'matrix' or a 'data.frame' or anything convertible to an " + "2-d 'matrix'."; + } + } + else + { + throw std::invalid_argument("unknown matrix type " + data.cppType); + } +} + +/** + * Return a string representing the command-line type of a matrix tuple option. + */ +template +std::string PrintTypeDoc( + util::ParamData& /* data */, + const typename std::enable_if>::value>::type*) +{ + return "A 2-d array containing 'numeric' data. Like the regular 2-d matrices" + ", this can be a 'matrix', or a data.frame. However, this type can also " + "accept a data.frame that has columns of type 'character', 'logical' or " + "'factor'. These values will be converted to numeric indices before " + "being passed to mlpack, and then inside mlpack they will be properly " + "treated as categorical variables, so there is no need to do one-hot " + "encoding for this matrix type."; +} + +/** + * Return a string representing the command-line type of a model. + */ +template +std::string PrintTypeDoc( + util::ParamData& /* data */, + const typename boost::disable_if>::type*, + const typename boost::enable_if>::type*) +{ + return "An mlpack model pointer. '' refers to the type of model that " + "is being stored, so, e.g., for 'cf()', the type will be 'CFModel'. " + "This type holds a pointer to C++ memory containing the mlpack model. " + "Note that this means the mlpack model itself cannot be easily inspected " + "in R. However, the pointer can be passed to subsequent calls to " + "mlpack functions, and can be serialized and deserialized via either the " + "'Serialize()' and 'Unserialize()' functions."; +} + +} // namespace r +} // namespace bindings +} // namespace mlpack + +#endif diff --git a/src/mlpack/bindings/R/r_method.cpp.in b/src/mlpack/bindings/R/r_method.cpp.in index 8ee09bcc3dd..6d927ce7f01 100644 --- a/src/mlpack/bindings/R/r_method.cpp.in +++ b/src/mlpack/bindings/R/r_method.cpp.in @@ -1,8 +1,8 @@ /** * @file src/${PROGRAM_NAME}.cpp * - * This is an autogenerated file containing implementations of C functions to be - * called by the R ${PROGRAM_NAME} binding. + * This is an autogenerated file containing implementations of C++ functions to + * be called by the R ${PROGRAM_NAME} binding. */ #include #define BINDING_TYPE BINDING_TYPE_R diff --git a/src/mlpack/bindings/go/CMakeLists.txt b/src/mlpack/bindings/go/CMakeLists.txt index 1d65ccd2917..e1456b62e17 100644 --- a/src/mlpack/bindings/go/CMakeLists.txt +++ b/src/mlpack/bindings/go/CMakeLists.txt @@ -224,7 +224,7 @@ if (BUILD_GO_BINDINGS) COMMAND ${CMAKE_COMMAND} -DGENERATE_BINDING_PROGRAM=${CMAKE_BINARY_DIR}/bin/generate_go_${name} -DBINDING_OUTPUT_FILE=${CMAKE_BINARY_DIR}/src/mlpack/bindings/go/src/mlpack.org/v1/mlpack/${name}.go - -P ${CMAKE_SOURCE_DIR}/CMake/GenerateGoBinding.cmake) + -P ${CMAKE_SOURCE_DIR}/CMake/GenerateBinding.cmake) add_dependencies(go generate_go_${name}) endif () diff --git a/src/mlpack/bindings/julia/get_julia_type.hpp b/src/mlpack/bindings/julia/get_julia_type.hpp index dd3220557d9..a3fa2c863ae 100644 --- a/src/mlpack/bindings/julia/get_julia_type.hpp +++ b/src/mlpack/bindings/julia/get_julia_type.hpp @@ -142,7 +142,7 @@ inline std::string GetJuliaType( { // Serializable types are just held as a pointer to nothing, but they're // wrapped in a struct. - std::string type = StripType(d.cppType); + std::string type = util::StripType(d.cppType); std::ostringstream oss; oss << type; return oss.str(); diff --git a/src/mlpack/bindings/markdown/default_param.hpp b/src/mlpack/bindings/markdown/default_param.hpp index 7e2980a7153..cf4a175a29c 100644 --- a/src/mlpack/bindings/markdown/default_param.hpp +++ b/src/mlpack/bindings/markdown/default_param.hpp @@ -20,6 +20,7 @@ #include #include #include +#include namespace mlpack { namespace bindings { @@ -54,6 +55,11 @@ void DefaultParam(util::ParamData& data, *((std::string*) output) = go::DefaultParamImpl::type>(data); } + else if (BindingInfo::Language() == "r") + { + *((std::string*) output) = + r::DefaultParamImpl::type>(data); + } else { throw std::invalid_argument("DefaultParam(): unknown " diff --git a/src/mlpack/bindings/markdown/get_binding_name.cpp b/src/mlpack/bindings/markdown/get_binding_name.cpp index 50627a1d16b..b3cf4e51e88 100644 --- a/src/mlpack/bindings/markdown/get_binding_name.cpp +++ b/src/mlpack/bindings/markdown/get_binding_name.cpp @@ -42,6 +42,11 @@ std::string GetBindingName(const std::string& language, // For Go bindings, the name is unchanged. return name; } + else if (language == "r") + { + // For R bindings, the name is unchanged. + return name; + } else { throw std::invalid_argument("Don't know how to compute binding name for " diff --git a/src/mlpack/bindings/markdown/get_printable_type.hpp b/src/mlpack/bindings/markdown/get_printable_type.hpp index 65a03d5d14f..2848947b540 100644 --- a/src/mlpack/bindings/markdown/get_printable_type.hpp +++ b/src/mlpack/bindings/markdown/get_printable_type.hpp @@ -19,6 +19,7 @@ #include #include #include +#include namespace mlpack { namespace bindings { @@ -53,6 +54,11 @@ void GetPrintableType(util::ParamData& data, *((std::string*) output) = go::GetPrintableType::type>(data); } + else if (BindingInfo::Language() == "r") + { + *((std::string*) output) = + r::GetPrintableType::type>(data); + } else { throw std::invalid_argument("GetPrintableType(): unknown " diff --git a/src/mlpack/bindings/markdown/print_doc_functions_impl.hpp b/src/mlpack/bindings/markdown/print_doc_functions_impl.hpp index da4718487aa..2d1c0ff4576 100644 --- a/src/mlpack/bindings/markdown/print_doc_functions_impl.hpp +++ b/src/mlpack/bindings/markdown/print_doc_functions_impl.hpp @@ -22,6 +22,7 @@ #include #include #include +#include namespace mlpack { namespace bindings { @@ -49,6 +50,10 @@ inline std::string GetBindingName(const std::string& bindingName) { return go::GetBindingName(bindingName); } + else if (BindingInfo::Language() == "r") + { + return r::GetBindingName(bindingName); + } else { throw std::invalid_argument("PrintValue(): unknown " @@ -77,6 +82,10 @@ inline std::string PrintLanguage(const std::string& language) { return "Go"; } + else if (language == "r") + { + return "R"; + } else { throw std::invalid_argument("PrintLanguage(): unknown " @@ -105,6 +114,10 @@ inline std::string PrintImport(const std::string& bindingName) { return go::PrintImport(); } + else if (BindingInfo::Language() == "r") + { + return r::PrintImport(); + } else { throw std::invalid_argument("PrintImport(): unknown " @@ -133,6 +146,10 @@ inline std::string PrintInputOptionInfo() { return go::PrintInputOptionInfo(); } + else if (BindingInfo::Language() == "r") + { + return r::PrintInputOptionInfo(); + } else { throw std::invalid_argument("PrintInputOptionInfo(): unknown " @@ -161,6 +178,10 @@ inline std::string PrintOutputOptionInfo() { return go::PrintOutputOptionInfo(); } + else if (BindingInfo::Language() == "r") + { + return r::PrintOutputOptionInfo(); + } else { throw std::invalid_argument("PrintOutputOptionInfo(): unknown " @@ -390,6 +411,10 @@ inline std::string PrintValue(const T& value, bool quotes) { result = go::PrintValue(value, quotes); } + else if (BindingInfo::Language() == "r") + { + result = r::PrintValue(value, quotes); + } else { throw std::invalid_argument("PrintValue(): unknown " @@ -433,6 +458,10 @@ inline std::string PrintDefault(const std::string& paramName) { oss << go::PrintDefault(paramName); } + else if (BindingInfo::Language() == "r") + { + oss << r::PrintDefault(paramName); + } else { throw std::invalid_argument("PrintDefault: unknown " @@ -465,6 +494,10 @@ inline std::string PrintDataset(const std::string& dataset) { result = go::PrintDataset(dataset); } + else if (BindingInfo::Language() == "r") + { + result = r::PrintDataset(dataset); + } else { throw std::invalid_argument("PrintDataset(): unknown " @@ -496,6 +529,10 @@ inline std::string PrintModel(const std::string& model) { result = go::PrintModel(model); } + else if (BindingInfo::Language() == "r") + { + result = r::PrintModel(model); + } else { throw std::invalid_argument("PrintModel(): unknown " @@ -534,6 +571,11 @@ std::string ProgramCall(const std::string& programName, Args... args) s += "```go\n"; s += go::ProgramCall(programName, args...); } + else if (BindingInfo::Language() == "r") + { + s += "```R\n"; + s += r::ProgramCall(true, programName, args...); + } else { throw std::invalid_argument("ProgramCall(): unknown " @@ -579,11 +621,19 @@ inline std::string ProgramCall(const std::string& programName) else if (BindingInfo::Language() == "go") { s += "go\n"; - std::string import = PrintImport(GetBindingName(programName)); + std::string import = PrintImport(programName); if (import.size() > 0) s += import + "\n"; s += go::ProgramCall(programName); } + else if (BindingInfo::Language() == "r") + { + s += "R\n"; + std::string import = PrintImport(programName); + if (import.size() > 0) + s += "R> " + import + "\n"; + s += r::ProgramCall(programName); + } else { throw std::invalid_argument("ProgramCall(): unknown " @@ -621,6 +671,10 @@ inline std::string ParamString(const std::string& paramName) { s = go::ParamString(paramName); } + else if (BindingInfo::Language() == "r") + { + s = r::ParamString(paramName); + } else { throw std::invalid_argument("ParamString(): unknown " @@ -668,6 +722,10 @@ inline bool IgnoreCheck(const T& t) { return go::IgnoreCheck(t); } + else if (BindingInfo::Language() == "r") + { + return r::IgnoreCheck(t); + } else { throw std::invalid_argument("IgnoreCheck(): unknown " diff --git a/src/mlpack/bindings/markdown/print_type_doc.hpp b/src/mlpack/bindings/markdown/print_type_doc.hpp index d997f6d6bee..34a1906fa05 100644 --- a/src/mlpack/bindings/markdown/print_type_doc.hpp +++ b/src/mlpack/bindings/markdown/print_type_doc.hpp @@ -19,6 +19,7 @@ #include #include #include +#include namespace mlpack { namespace bindings { @@ -47,6 +48,10 @@ std::string PrintTypeDoc(util::ParamData& data) { return go::PrintTypeDoc::type>(data); } + else if (BindingInfo::Language() == "r") + { + return r::PrintTypeDoc::type>(data); + } else { throw std::invalid_argument("PrintTypeDoc(): unknown " diff --git a/src/mlpack/core/util/mlpack_main.hpp b/src/mlpack/core/util/mlpack_main.hpp index 31c5b919bd4..8c0b2613c7a 100644 --- a/src/mlpack/core/util/mlpack_main.hpp +++ b/src/mlpack/core/util/mlpack_main.hpp @@ -346,7 +346,7 @@ PARAM_FLAG("verbose", "Display informational messages and the full list of " #define PRINT_PARAM_VALUE mlpack::bindings::r::PrintValue #define PRINT_DATASET mlpack::bindings::r::PrintDataset #define PRINT_MODEL mlpack::bindings::r::PrintModel -#define PRINT_CALL mlpack::bindings::r::ProgramCall +#define PRINT_CALL(...) mlpack::bindings::r::ProgramCall(false, __VA_ARGS__) #define BINDING_IGNORE_CHECK mlpack::bindings::r::IgnoreCheck namespace mlpack { diff --git a/src/mlpack/methods/adaboost/CMakeLists.txt b/src/mlpack/methods/adaboost/CMakeLists.txt index 4792cbfc705..102c41c488f 100644 --- a/src/mlpack/methods/adaboost/CMakeLists.txt +++ b/src/mlpack/methods/adaboost/CMakeLists.txt @@ -21,4 +21,4 @@ add_python_binding(adaboost) add_julia_binding(adaboost) add_go_binding(adaboost) add_r_binding(adaboost) -add_markdown_docs(adaboost "cli;python;julia;go" "classification") +add_markdown_docs(adaboost "cli;python;julia;go;r" "classification") diff --git a/src/mlpack/methods/approx_kfn/CMakeLists.txt b/src/mlpack/methods/approx_kfn/CMakeLists.txt index 0bb120fcb7b..f7694251278 100644 --- a/src/mlpack/methods/approx_kfn/CMakeLists.txt +++ b/src/mlpack/methods/approx_kfn/CMakeLists.txt @@ -24,4 +24,4 @@ add_python_binding(approx_kfn) add_julia_binding(approx_kfn) add_go_binding(approx_kfn) add_r_binding(approx_kfn) -add_markdown_docs(approx_kfn "cli;python;julia;go" "geometry") +add_markdown_docs(approx_kfn "cli;python;julia;go;r" "geometry") diff --git a/src/mlpack/methods/cf/CMakeLists.txt b/src/mlpack/methods/cf/CMakeLists.txt index 4fef8e559e4..a7c552ae28b 100644 --- a/src/mlpack/methods/cf/CMakeLists.txt +++ b/src/mlpack/methods/cf/CMakeLists.txt @@ -28,4 +28,4 @@ add_python_binding(cf) add_julia_binding(cf) add_go_binding(cf) add_r_binding(cf) -add_markdown_docs(cf "cli;python;julia;go" "misc. / other") +add_markdown_docs(cf "cli;python;julia;go;r" "misc. / other") diff --git a/src/mlpack/methods/dbscan/CMakeLists.txt b/src/mlpack/methods/dbscan/CMakeLists.txt index 13de5dbdcc1..7c0a883504a 100644 --- a/src/mlpack/methods/dbscan/CMakeLists.txt +++ b/src/mlpack/methods/dbscan/CMakeLists.txt @@ -21,4 +21,4 @@ add_python_binding(dbscan) add_julia_binding(dbscan) add_go_binding(dbscan) add_r_binding(dbscan) -add_markdown_docs(dbscan "cli;python;julia;go" "clustering") +add_markdown_docs(dbscan "cli;python;julia;go;r" "clustering") diff --git a/src/mlpack/methods/decision_stump/CMakeLists.txt b/src/mlpack/methods/decision_stump/CMakeLists.txt index 129155b772b..3f172b7d872 100644 --- a/src/mlpack/methods/decision_stump/CMakeLists.txt +++ b/src/mlpack/methods/decision_stump/CMakeLists.txt @@ -19,4 +19,4 @@ add_python_binding(decision_stump) add_julia_binding(decision_stump) add_go_binding(decision_stump) add_r_binding(decision_stump) -add_markdown_docs(decision_stump "cli;python;julia;go" "classification") +add_markdown_docs(decision_stump "cli;python;julia;go;r" "classification") diff --git a/src/mlpack/methods/decision_tree/CMakeLists.txt b/src/mlpack/methods/decision_tree/CMakeLists.txt index f84a99a8ce7..68f5a2ef41f 100644 --- a/src/mlpack/methods/decision_tree/CMakeLists.txt +++ b/src/mlpack/methods/decision_tree/CMakeLists.txt @@ -28,4 +28,4 @@ add_python_binding(decision_tree) add_julia_binding(decision_tree) add_go_binding(decision_tree) add_r_binding(decision_tree) -add_markdown_docs(decision_tree "cli;python;julia;go" "classification") +add_markdown_docs(decision_tree "cli;python;julia;go;r" "classification") diff --git a/src/mlpack/methods/det/CMakeLists.txt b/src/mlpack/methods/det/CMakeLists.txt index e872ba3114b..2d35bd9fb8f 100644 --- a/src/mlpack/methods/det/CMakeLists.txt +++ b/src/mlpack/methods/det/CMakeLists.txt @@ -24,4 +24,4 @@ add_python_binding(det) add_julia_binding(det) add_go_binding(det) add_r_binding(det) -add_markdown_docs(det "cli;python;julia;go" "misc. / other") +add_markdown_docs(det "cli;python;julia;go;r" "misc. / other") diff --git a/src/mlpack/methods/emst/CMakeLists.txt b/src/mlpack/methods/emst/CMakeLists.txt index 2de18b2712b..4d7fd2cd4ce 100644 --- a/src/mlpack/methods/emst/CMakeLists.txt +++ b/src/mlpack/methods/emst/CMakeLists.txt @@ -26,4 +26,4 @@ add_python_binding(emst) add_julia_binding(emst) add_go_binding(emst) add_r_binding(emst) -add_markdown_docs(emst "cli;python;julia;go" "geometry") +add_markdown_docs(emst "cli;python;julia;go;r" "geometry") diff --git a/src/mlpack/methods/fastmks/CMakeLists.txt b/src/mlpack/methods/fastmks/CMakeLists.txt index 1c0d7549fad..78a11b535c2 100644 --- a/src/mlpack/methods/fastmks/CMakeLists.txt +++ b/src/mlpack/methods/fastmks/CMakeLists.txt @@ -25,4 +25,4 @@ add_python_binding(fastmks) add_julia_binding(fastmks) add_go_binding(fastmks) add_r_binding(fastmks) -add_markdown_docs(fastmks "cli;python;julia;go" "geometry") +add_markdown_docs(fastmks "cli;python;julia;go;r" "geometry") diff --git a/src/mlpack/methods/gmm/CMakeLists.txt b/src/mlpack/methods/gmm/CMakeLists.txt index 0dfcc7c2e8d..52d98b7c1ed 100644 --- a/src/mlpack/methods/gmm/CMakeLists.txt +++ b/src/mlpack/methods/gmm/CMakeLists.txt @@ -29,18 +29,18 @@ add_python_binding(gmm_train) add_julia_binding(gmm_train) add_go_binding(gmm_train) add_r_binding(gmm_train) -add_markdown_docs(gmm_train "cli;python;julia;go" "clustering") +add_markdown_docs(gmm_train "cli;python;julia;go;r" "clustering") add_cli_executable(gmm_generate) add_python_binding(gmm_generate) add_julia_binding(gmm_generate) add_go_binding(gmm_generate) add_r_binding(gmm_generate) -add_markdown_docs(gmm_generate "cli;python;julia;go" "clustering") +add_markdown_docs(gmm_generate "cli;python;julia;go;r" "clustering") add_cli_executable(gmm_probability) add_python_binding(gmm_probability) add_julia_binding(gmm_probability) add_go_binding(gmm_probability) add_r_binding(gmm_probability) -add_markdown_docs(gmm_probability "cli;python;julia;go" "clustering") +add_markdown_docs(gmm_probability "cli;python;julia;go;r" "clustering") diff --git a/src/mlpack/methods/hmm/CMakeLists.txt b/src/mlpack/methods/hmm/CMakeLists.txt index e644f7b67a9..bfe2cedc583 100644 --- a/src/mlpack/methods/hmm/CMakeLists.txt +++ b/src/mlpack/methods/hmm/CMakeLists.txt @@ -24,25 +24,25 @@ add_python_binding(hmm_train) add_julia_binding(hmm_train) add_go_binding(hmm_train) add_r_binding(hmm_train) -add_markdown_docs(hmm_train "cli;python;julia;go" "misc. / other") +add_markdown_docs(hmm_train "cli;python;julia;go;r" "misc. / other") add_cli_executable(hmm_loglik) add_python_binding(hmm_loglik) add_julia_binding(hmm_loglik) add_go_binding(hmm_loglik) add_r_binding(hmm_loglik) -add_markdown_docs(hmm_loglik "cli;python;julia;go" "misc. / other") +add_markdown_docs(hmm_loglik "cli;python;julia;go;r" "misc. / other") add_cli_executable(hmm_viterbi) add_python_binding(hmm_viterbi) add_julia_binding(hmm_viterbi) add_go_binding(hmm_viterbi) add_r_binding(hmm_viterbi) -add_markdown_docs(hmm_viterbi "cli;python;julia;go" "misc. / other") +add_markdown_docs(hmm_viterbi "cli;python;julia;go;r" "misc. / other") add_cli_executable(hmm_generate) add_python_binding(hmm_generate) add_julia_binding(hmm_generate) add_go_binding(hmm_generate) add_r_binding(hmm_generate) -add_markdown_docs(hmm_generate "cli;python;julia;go" "misc. / other") +add_markdown_docs(hmm_generate "cli;python;julia;go;r" "misc. / other") diff --git a/src/mlpack/methods/hoeffding_trees/CMakeLists.txt b/src/mlpack/methods/hoeffding_trees/CMakeLists.txt index 85a2091de54..cd679cc55ec 100644 --- a/src/mlpack/methods/hoeffding_trees/CMakeLists.txt +++ b/src/mlpack/methods/hoeffding_trees/CMakeLists.txt @@ -33,4 +33,4 @@ add_python_binding(hoeffding_tree) add_julia_binding(hoeffding_tree) add_go_binding(hoeffding_tree) add_r_binding(hoeffding_tree) -add_markdown_docs(hoeffding_tree "cli;python;julia;go" "classification") +add_markdown_docs(hoeffding_tree "cli;python;julia;go;r" "classification") diff --git a/src/mlpack/methods/kde/CMakeLists.txt b/src/mlpack/methods/kde/CMakeLists.txt index b2bec3b3860..31dacaee437 100644 --- a/src/mlpack/methods/kde/CMakeLists.txt +++ b/src/mlpack/methods/kde/CMakeLists.txt @@ -24,4 +24,4 @@ add_python_binding(kde) add_julia_binding(kde) add_go_binding(kde) add_r_binding(kde) -add_markdown_docs(kde "cli;python;julia;go" "misc. / other") +add_markdown_docs(kde "cli;python;julia;go;r" "misc. / other") diff --git a/src/mlpack/methods/kernel_pca/CMakeLists.txt b/src/mlpack/methods/kernel_pca/CMakeLists.txt index 090ba4830ca..61d49b5a264 100644 --- a/src/mlpack/methods/kernel_pca/CMakeLists.txt +++ b/src/mlpack/methods/kernel_pca/CMakeLists.txt @@ -21,4 +21,4 @@ add_python_binding(kernel_pca) add_julia_binding(kernel_pca) add_go_binding(kernel_pca) add_r_binding(kernel_pca) -add_markdown_docs(kernel_pca "cli;python;julia;go" "transformations") +add_markdown_docs(kernel_pca "cli;python;julia;go;r" "transformations") diff --git a/src/mlpack/methods/kmeans/CMakeLists.txt b/src/mlpack/methods/kmeans/CMakeLists.txt index ae5f7d23d28..1dbbbba6266 100644 --- a/src/mlpack/methods/kmeans/CMakeLists.txt +++ b/src/mlpack/methods/kmeans/CMakeLists.txt @@ -43,4 +43,4 @@ add_python_binding(kmeans) add_julia_binding(kmeans) add_go_binding(kmeans) add_r_binding(kmeans) -add_markdown_docs(kmeans "cli;python;julia;go" "clustering") +add_markdown_docs(kmeans "cli;python;julia;go;r" "clustering") diff --git a/src/mlpack/methods/lars/CMakeLists.txt b/src/mlpack/methods/lars/CMakeLists.txt index e90f8d430a0..df7d973cdeb 100644 --- a/src/mlpack/methods/lars/CMakeLists.txt +++ b/src/mlpack/methods/lars/CMakeLists.txt @@ -19,4 +19,4 @@ add_python_binding(lars) add_julia_binding(lars) add_go_binding(lars) add_r_binding(lars) -add_markdown_docs(lars "cli;python;julia;go" "regression") +add_markdown_docs(lars "cli;python;julia;go;r" "regression") diff --git a/src/mlpack/methods/linear_regression/CMakeLists.txt b/src/mlpack/methods/linear_regression/CMakeLists.txt index 29ac369579e..bfb2bdb25b9 100644 --- a/src/mlpack/methods/linear_regression/CMakeLists.txt +++ b/src/mlpack/methods/linear_regression/CMakeLists.txt @@ -20,4 +20,4 @@ add_python_binding(linear_regression) add_julia_binding(linear_regression) add_go_binding(linear_regression) add_r_binding(linear_regression) -add_markdown_docs(linear_regression "cli;python;julia;go" "regression") +add_markdown_docs(linear_regression "cli;python;julia;go;r" "regression") diff --git a/src/mlpack/methods/linear_svm/CMakeLists.txt b/src/mlpack/methods/linear_svm/CMakeLists.txt index cec2822f6ab..937cad9c5f1 100644 --- a/src/mlpack/methods/linear_svm/CMakeLists.txt +++ b/src/mlpack/methods/linear_svm/CMakeLists.txt @@ -22,4 +22,4 @@ add_python_binding(linear_svm) add_go_binding(linear_svm) add_julia_binding(linear_svm) add_r_binding(linear_svm) -add_markdown_docs(linear_svm "cli;python;julia;go" "classification") +add_markdown_docs(linear_svm "cli;python;julia;go;r" "classification") diff --git a/src/mlpack/methods/lmnn/CMakeLists.txt b/src/mlpack/methods/lmnn/CMakeLists.txt index d41cbccdf4f..f383a496577 100644 --- a/src/mlpack/methods/lmnn/CMakeLists.txt +++ b/src/mlpack/methods/lmnn/CMakeLists.txt @@ -23,4 +23,4 @@ add_python_binding(lmnn) add_julia_binding(lmnn) add_go_binding(lmnn) add_r_binding(lmnn) -add_markdown_docs(lmnn "cli;python;julia;go" "transformations") +add_markdown_docs(lmnn "cli;python;julia;go;r" "transformations") diff --git a/src/mlpack/methods/local_coordinate_coding/CMakeLists.txt b/src/mlpack/methods/local_coordinate_coding/CMakeLists.txt index 7db7a2d5b49..dd5124bb37c 100644 --- a/src/mlpack/methods/local_coordinate_coding/CMakeLists.txt +++ b/src/mlpack/methods/local_coordinate_coding/CMakeLists.txt @@ -23,4 +23,4 @@ add_python_binding(local_coordinate_coding) add_julia_binding(local_coordinate_coding) add_go_binding(local_coordinate_coding) add_r_binding(local_coordinate_coding) -add_markdown_docs(local_coordinate_coding "cli;python;julia;go" "transformations") +add_markdown_docs(local_coordinate_coding "cli;python;julia;go;r" "transformations") diff --git a/src/mlpack/methods/logistic_regression/CMakeLists.txt b/src/mlpack/methods/logistic_regression/CMakeLists.txt index 1e4afcecf34..f5a00bccc61 100644 --- a/src/mlpack/methods/logistic_regression/CMakeLists.txt +++ b/src/mlpack/methods/logistic_regression/CMakeLists.txt @@ -22,4 +22,4 @@ add_python_binding(logistic_regression) add_julia_binding(logistic_regression) add_go_binding(logistic_regression) add_r_binding(logistic_regression) -add_markdown_docs(logistic_regression "cli;python;julia;go" "classification") +add_markdown_docs(logistic_regression "cli;python;julia;go;r" "classification") diff --git a/src/mlpack/methods/lsh/CMakeLists.txt b/src/mlpack/methods/lsh/CMakeLists.txt index 9ebe9f3d78c..79fa17b44e8 100644 --- a/src/mlpack/methods/lsh/CMakeLists.txt +++ b/src/mlpack/methods/lsh/CMakeLists.txt @@ -22,4 +22,4 @@ add_python_binding(lsh) add_julia_binding(lsh) add_go_binding(lsh) add_r_binding(lsh) -add_markdown_docs(lsh "cli;python;julia;go" "geometry") +add_markdown_docs(lsh "cli;python;julia;go;r" "geometry") diff --git a/src/mlpack/methods/mean_shift/CMakeLists.txt b/src/mlpack/methods/mean_shift/CMakeLists.txt index 01b776d7f08..2ad50335201 100644 --- a/src/mlpack/methods/mean_shift/CMakeLists.txt +++ b/src/mlpack/methods/mean_shift/CMakeLists.txt @@ -19,4 +19,4 @@ add_python_binding(mean_shift) add_julia_binding(mean_shift) add_go_binding(mean_shift) add_r_binding(mean_shift) -add_markdown_docs(mean_shift "cli;python;julia;go" "clustering") +add_markdown_docs(mean_shift "cli;python;julia;go;r" "clustering") diff --git a/src/mlpack/methods/naive_bayes/CMakeLists.txt b/src/mlpack/methods/naive_bayes/CMakeLists.txt index f0c6a44a53d..85ab2beb5e1 100644 --- a/src/mlpack/methods/naive_bayes/CMakeLists.txt +++ b/src/mlpack/methods/naive_bayes/CMakeLists.txt @@ -19,4 +19,4 @@ add_python_binding(nbc) add_julia_binding(nbc) add_go_binding(nbc) add_r_binding(nbc) -add_markdown_docs(nbc "cli;python;julia;go" "classification") +add_markdown_docs(nbc "cli;python;julia;go;r" "classification") diff --git a/src/mlpack/methods/nca/CMakeLists.txt b/src/mlpack/methods/nca/CMakeLists.txt index cb40a558c6b..e956d76a6a9 100644 --- a/src/mlpack/methods/nca/CMakeLists.txt +++ b/src/mlpack/methods/nca/CMakeLists.txt @@ -21,4 +21,4 @@ add_python_binding(nca) add_julia_binding(nca) add_go_binding(nca) add_r_binding(nca) -add_markdown_docs(nca "cli;python;julia;go" "transformations") +add_markdown_docs(nca "cli;python;julia;go;r" "transformations") diff --git a/src/mlpack/methods/neighbor_search/CMakeLists.txt b/src/mlpack/methods/neighbor_search/CMakeLists.txt index 1044a4db8f7..ce24ba085fd 100644 --- a/src/mlpack/methods/neighbor_search/CMakeLists.txt +++ b/src/mlpack/methods/neighbor_search/CMakeLists.txt @@ -32,11 +32,11 @@ add_python_binding(knn) add_julia_binding(knn) add_go_binding(knn) add_r_binding(knn) -add_markdown_docs(knn "cli;python;julia;go" "geometry") +add_markdown_docs(knn "cli;python;julia;go;r" "geometry") add_cli_executable(kfn) add_python_binding(kfn) add_julia_binding(kfn) add_go_binding(kfn) add_r_binding(kfn) -add_markdown_docs(kfn "cli;python;julia;go" "geometry") +add_markdown_docs(kfn "cli;python;julia;go;r" "geometry") diff --git a/src/mlpack/methods/nmf/CMakeLists.txt b/src/mlpack/methods/nmf/CMakeLists.txt index c1ed95d895f..7f93ae35026 100644 --- a/src/mlpack/methods/nmf/CMakeLists.txt +++ b/src/mlpack/methods/nmf/CMakeLists.txt @@ -3,4 +3,4 @@ add_python_binding(nmf) add_julia_binding(nmf) add_go_binding(nmf) add_r_binding(nmf) -add_markdown_docs(nmf "cli;python;julia;go" "misc. / other") +add_markdown_docs(nmf "cli;python;julia;go;r" "misc. / other") diff --git a/src/mlpack/methods/pca/CMakeLists.txt b/src/mlpack/methods/pca/CMakeLists.txt index 12cbf7ac33a..6ed7d726d89 100644 --- a/src/mlpack/methods/pca/CMakeLists.txt +++ b/src/mlpack/methods/pca/CMakeLists.txt @@ -21,4 +21,4 @@ add_python_binding(pca) add_julia_binding(pca) add_go_binding(pca) add_r_binding(pca) -add_markdown_docs(pca "cli;python;julia;go" "transformations") +add_markdown_docs(pca "cli;python;julia;go;r" "transformations") diff --git a/src/mlpack/methods/perceptron/CMakeLists.txt b/src/mlpack/methods/perceptron/CMakeLists.txt index a51f082ce44..1315d086082 100644 --- a/src/mlpack/methods/perceptron/CMakeLists.txt +++ b/src/mlpack/methods/perceptron/CMakeLists.txt @@ -22,4 +22,4 @@ add_python_binding(perceptron) add_julia_binding(perceptron) add_go_binding(perceptron) add_r_binding(perceptron) -add_markdown_docs(perceptron "cli;python;julia;go" "classification") +add_markdown_docs(perceptron "cli;python;julia;go;r" "classification") diff --git a/src/mlpack/methods/preprocess/CMakeLists.txt b/src/mlpack/methods/preprocess/CMakeLists.txt index 385075ea1f6..eb6ef7df15c 100644 --- a/src/mlpack/methods/preprocess/CMakeLists.txt +++ b/src/mlpack/methods/preprocess/CMakeLists.txt @@ -21,21 +21,21 @@ add_python_binding(preprocess_split) add_julia_binding(preprocess_split) add_go_binding(preprocess_split) add_r_binding(preprocess_split) -add_markdown_docs(preprocess_split "cli;python;julia;go" "preprocessing") +add_markdown_docs(preprocess_split "cli;python;julia;go;r" "preprocessing") add_cli_executable(preprocess_binarize) add_python_binding(preprocess_binarize) add_julia_binding(preprocess_binarize) add_go_binding(preprocess_binarize) add_r_binding(preprocess_binarize) -add_markdown_docs(preprocess_binarize "cli;python;julia;go" "preprocessing") +add_markdown_docs(preprocess_binarize "cli;python;julia;go;r" "preprocessing") add_cli_executable(preprocess_describe) add_python_binding(preprocess_describe) add_julia_binding(preprocess_describe) add_go_binding(preprocess_describe) add_r_binding(preprocess_describe) -add_markdown_docs(preprocess_describe "cli;python;julia;go" "preprocessing") +add_markdown_docs(preprocess_describe "cli;python;julia;go;r" "preprocessing") #add_cli_executable(preprocess_scan) @@ -43,6 +43,7 @@ add_cli_executable(preprocess_imputer) #add_go_binding(preprocess_imputer) #add_python_binding(preprocess_imputer) #add_julia_binding(preprocess_imputer) +#add_r_binding(preprocess_imputer) add_markdown_docs(preprocess_imputer "cli" "preprocessing") add_cli_executable(preprocess_scale) @@ -50,7 +51,7 @@ add_python_binding(preprocess_scale) add_go_binding(preprocess_scale) add_julia_binding(preprocess_scale) add_r_binding(preprocess_scale) -add_markdown_docs(preprocess_scale "cli;python;julia;go" "preprocessing") +add_markdown_docs(preprocess_scale "cli;python;julia;go;r" "preprocessing") if (STB_AVAILABLE) add_cli_executable(image_converter) @@ -58,5 +59,5 @@ if (STB_AVAILABLE) add_julia_binding(image_converter) add_go_binding(image_converter) add_r_binding(image_converter) - add_markdown_docs(image_converter "cli;python;julia;go" "preprocessing") + add_markdown_docs(image_converter "cli;python;julia;go;r" "preprocessing") endif () diff --git a/src/mlpack/methods/radical/CMakeLists.txt b/src/mlpack/methods/radical/CMakeLists.txt index 39544f42818..723f61e158f 100644 --- a/src/mlpack/methods/radical/CMakeLists.txt +++ b/src/mlpack/methods/radical/CMakeLists.txt @@ -18,4 +18,4 @@ add_python_binding(radical) add_julia_binding(radical) add_go_binding(radical) add_r_binding(radical) -add_markdown_docs(radical "cli;python;julia;go" "transformations") +add_markdown_docs(radical "cli;python;julia;go;r" "transformations") diff --git a/src/mlpack/methods/random_forest/CMakeLists.txt b/src/mlpack/methods/random_forest/CMakeLists.txt index 2a9e552acb2..4be75d37618 100644 --- a/src/mlpack/methods/random_forest/CMakeLists.txt +++ b/src/mlpack/methods/random_forest/CMakeLists.txt @@ -20,4 +20,4 @@ add_python_binding(random_forest) add_julia_binding(random_forest) add_go_binding(random_forest) add_r_binding(random_forest) -add_markdown_docs(random_forest "cli;python;julia;go" "classification") +add_markdown_docs(random_forest "cli;python;julia;go;r" "classification") diff --git a/src/mlpack/methods/range_search/CMakeLists.txt b/src/mlpack/methods/range_search/CMakeLists.txt index 2b884fe1ce3..0a1912b6b4d 100644 --- a/src/mlpack/methods/range_search/CMakeLists.txt +++ b/src/mlpack/methods/range_search/CMakeLists.txt @@ -24,4 +24,4 @@ add_cli_executable(range_search) #add_julia_binding(range_search) #add_go_binding(range_search) #add_r_binding(range_search) -add_markdown_docs(range_search "cli;go" "geometry") +add_markdown_docs(range_search "cli" "geometry") diff --git a/src/mlpack/methods/rann/CMakeLists.txt b/src/mlpack/methods/rann/CMakeLists.txt index b7b90e0c8bd..99e838b4590 100644 --- a/src/mlpack/methods/rann/CMakeLists.txt +++ b/src/mlpack/methods/rann/CMakeLists.txt @@ -40,4 +40,4 @@ add_python_binding(krann) add_julia_binding(krann) add_go_binding(krann) add_r_binding(krann) -add_markdown_docs(krann "cli;python;julia;go" "geometry") +add_markdown_docs(krann "cli;python;julia;go;r" "geometry") diff --git a/src/mlpack/methods/softmax_regression/CMakeLists.txt b/src/mlpack/methods/softmax_regression/CMakeLists.txt index 23786feceb2..d245fa4547a 100644 --- a/src/mlpack/methods/softmax_regression/CMakeLists.txt +++ b/src/mlpack/methods/softmax_regression/CMakeLists.txt @@ -22,4 +22,4 @@ add_python_binding(softmax_regression) add_julia_binding(softmax_regression) add_go_binding(softmax_regression) add_r_binding(softmax_regression) -add_markdown_docs(softmax_regression "cli;python;julia;go" "classification") +add_markdown_docs(softmax_regression "cli;python;julia;go;r" "classification") diff --git a/src/mlpack/methods/sparse_coding/CMakeLists.txt b/src/mlpack/methods/sparse_coding/CMakeLists.txt index afca2157ac5..45b627bcc08 100644 --- a/src/mlpack/methods/sparse_coding/CMakeLists.txt +++ b/src/mlpack/methods/sparse_coding/CMakeLists.txt @@ -23,4 +23,4 @@ add_python_binding(sparse_coding) add_julia_binding(sparse_coding) add_go_binding(sparse_coding) add_r_binding(sparse_coding) -add_markdown_docs(sparse_coding "cli;python;julia;go" "transformations") +add_markdown_docs(sparse_coding "cli;python;julia;go;r" "transformations") From 4e406127d18ce5c2438013b0ef730751474dcd3a Mon Sep 17 00:00:00 2001 From: Yashwant Singh Parihar Date: Mon, 27 Jul 2020 10:54:46 +0530 Subject: [PATCH 02/11] Update doc/guide/r_quickstart.hpp Co-authored-by: James J Balamuta --- doc/guide/r_quickstart.hpp | 1 + 1 file changed, 1 insertion(+) diff --git a/doc/guide/r_quickstart.hpp b/doc/guide/r_quickstart.hpp index 20c44df1217..a351381ebc6 100644 --- a/doc/guide/r_quickstart.hpp +++ b/doc/guide/r_quickstart.hpp @@ -38,6 +38,7 @@ print the accuracy of the random forest on the test dataset. You can copy-paste this code directly into R to run it. @code{.R} +if(!requireNamespace("data.table", quietly = TRUE)) { install.packages("data.table") } suppressMessages({ library("mlpack") library("data.table") From 1409c945781a5baa8a2c7f8fc304e704e3ce623f Mon Sep 17 00:00:00 2001 From: Yashwant Date: Mon, 27 Jul 2020 15:16:26 +0530 Subject: [PATCH 03/11] Add proper website. --- doc/guide/r_quickstart.hpp | 1 + src/mlpack/bindings/R/mlpack/DESCRIPTION.in | 5 +++-- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/doc/guide/r_quickstart.hpp b/doc/guide/r_quickstart.hpp index a351381ebc6..25325e3b8c0 100644 --- a/doc/guide/r_quickstart.hpp +++ b/doc/guide/r_quickstart.hpp @@ -109,6 +109,7 @@ train to give recommendations. You can copy-paste this code directly into R to run it. @code{.R} +if(!requireNamespace("data.table", quietly = TRUE)) { install.packages("data.table") } suppressMessages({ library("mlpack") library("data.table") diff --git a/src/mlpack/bindings/R/mlpack/DESCRIPTION.in b/src/mlpack/bindings/R/mlpack/DESCRIPTION.in index 6e30ef028fd..3cb2cda25c4 100644 --- a/src/mlpack/bindings/R/mlpack/DESCRIPTION.in +++ b/src/mlpack/bindings/R/mlpack/DESCRIPTION.in @@ -1,5 +1,5 @@ Package: mlpack -Title: 'Rcpp' Integration for the 'MLPACK' Library +Title: 'Rcpp' Integration for the 'mlpack' Library Version: @PACKAGE_VERSION@ Date: @PACKAGE_DATE@ Author: mlpack Team @@ -17,7 +17,8 @@ LinkingTo: Rcpp, BH (>= @BH_Version@), RcppEnsmallen (>= @RcppEnsmallen_Version@) Suggests: testthat (>= 2.1.0) -URL: http://www.mlpack.org/ +URL: https://www.mlpack.org/doc/mlpack-@PACKAGE_VERSION@/r_documentation.html, + https://github.com/mlpack/mlpack-r, https://github.com/mlpack/mlpack BugReports: https://github.com/mlpack/mlpack/issues LazyData: true RoxygenNote: 7.1.0 From 037dc7070e68c3483fadcef6ba9d0a76250c1233 Mon Sep 17 00:00:00 2001 From: Yashwant Singh Parihar Date: Fri, 31 Jul 2020 18:14:01 +0530 Subject: [PATCH 04/11] Apply suggestions from code review Co-authored-by: Ryan Curtin Co-authored-by: James J Balamuta --- README.md | 2 +- doc/guide/r_quickstart.hpp | 10 +++++----- src/mlpack/bindings/R/print_type_doc_impl.hpp | 6 +++--- 3 files changed, 9 insertions(+), 9 deletions(-) diff --git a/README.md b/README.md index 94b3d668271..8fc208fb583 100644 --- a/README.md +++ b/README.md @@ -122,7 +122,7 @@ If you would like to build the Julia bindings, make sure that Julia >= 1.3.0 is installed. If you would like to build the Go bindings, make sure that Go >= 1.11.0 is -installed with this package. +installed with this package: gonum diff --git a/doc/guide/r_quickstart.hpp b/doc/guide/r_quickstart.hpp index 25325e3b8c0..e37cd2aa86a 100644 --- a/doc/guide/r_quickstart.hpp +++ b/doc/guide/r_quickstart.hpp @@ -13,15 +13,17 @@ This quickstart guide is also available for @ref python_quickstart "Python" @ref cli_quickstart "the command-line", @ref julia_quickstart "Julia" and @ref go_quickstart "Go". -@section r_quickstart_install Installing mlpack +@section r_quickstart_install Installing mlpack binary package Installing the mlpack bindings for R is straightforward; you can just use -cran mirror: +CRAN mirror: @code{.R} install.packages('mlpack') @endcode +@section r_quickstart_install Installing mlpack package from source + Building the R bindings from scratch is a little more in-depth, though. For information on that, follow the instructions on the @ref build page, and be sure to specify @c -DBUILD_R_BINDINGS=ON to CMake; you may need to also set the @@ -167,9 +169,7 @@ Recommendations for user 1: @section r_quickstart_nextsteps Next steps with mlpack -Now that you have done some simple work with mlpack, you have seen how it can -easily plug into a data science workflow in R. A great thing to do next -would be to look at more documentation for the R mlpack bindings: +After working through this overview to `mlpack`'s R package, we hope you are inspired to use `mlpack`' in your data science workflow. We recommend as part of your next steps to look at more documentation for the R mlpack bindings: - R mlpack binding documentation diff --git a/src/mlpack/bindings/R/print_type_doc_impl.hpp b/src/mlpack/bindings/R/print_type_doc_impl.hpp index 878bfb836a5..71dc6404951 100644 --- a/src/mlpack/bindings/R/print_type_doc_impl.hpp +++ b/src/mlpack/bindings/R/print_type_doc_impl.hpp @@ -53,7 +53,7 @@ std::string PrintTypeDoc( // Not sure what it is... else { - throw std::invalid_argument("unknown parameter type " + data.cppType); + throw std::invalid_argument("Unknown parameter type '" + data.cppType + "'."); } } @@ -75,7 +75,7 @@ std::string PrintTypeDoc( } else { - throw std::invalid_argument("unknown vector type " + data.cppType); + throw std::invalid_argument("Unknown vector type '" + data.cppType + "'."); } } @@ -117,7 +117,7 @@ std::string PrintTypeDoc( } else { - throw std::invalid_argument("unknown matrix type " + data.cppType); + throw std::invalid_argument("Unknown matrix type '" + data.cppType + "'."); } } From e9f6225202819c31d483958f0df3e8947053d99d Mon Sep 17 00:00:00 2001 From: Yashwant Date: Fri, 31 Jul 2020 18:40:12 +0530 Subject: [PATCH 05/11] Resolve Comments. --- CMakeLists.txt | 11 ++++---- README.md | 2 +- doc/guide/r_quickstart.hpp | 6 ++-- src/mlpack/bindings/R/CMakeLists.txt | 4 +-- src/mlpack/bindings/R/mlpack/DESCRIPTION.in | 2 +- src/mlpack/bindings/R/mlpack/src/r_util.cpp | 28 +++++++++---------- .../R/mlpack/tests/testthat/test-R_binding.R | 4 +-- .../bindings/R/tests/test_r_binding_main.cpp | 4 +-- 8 files changed, 31 insertions(+), 30 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 95f1efd46e5..92b03457c50 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -19,6 +19,11 @@ option(DOWNLOAD_STB_IMAGE "Download stb_image for image loading." ON) option(BUILD_PYTHON_BINDINGS "Build Python bindings." ON) option(BUILD_GO_SHLIB "Build Go shared library." OFF) +# Set minimum library version required by mlpack. +set(ARMADILLO_VERSION "8.400.0") +set(ENSMALLEN_VERSION "2.10.0") +set(BOOST_VERSION "1.58") + if (WIN32) option(BUILD_SHARED_LIBS "Compile shared libraries (if OFF, static libraries are compiled)." OFF) @@ -278,12 +283,6 @@ endif() # ENSMALLEN_INCLUDE_DIR - include directory for ensmallen # STB_IMAGE_INCLUDE_DIR - include directory for STB image library # MATHJAX_ROOT - root of MathJax installation - -# Set minimum library version required by mlpack. -set(ARMADILLO_VERSION "8.400.0") -set(ENSMALLEN_VERSION "2.10.0") -set(BOOST_VERSION "1.58") - find_package(Armadillo "${ARMADILLO_VERSION}" REQUIRED) # Include directories for the previous dependencies. diff --git a/README.md b/README.md index 8fc208fb583..ce523ff093c 100644 --- a/README.md +++ b/README.md @@ -126,7 +126,7 @@ installed with this package: gonum -If you would like to build the R bindings, make sure that R >= 3.5 is +If you would like to build the R bindings, make sure that R >= 4.0 is installed with these R packages. Rcpp >= 0.12.12 diff --git a/doc/guide/r_quickstart.hpp b/doc/guide/r_quickstart.hpp index e37cd2aa86a..a66d292a92c 100644 --- a/doc/guide/r_quickstart.hpp +++ b/doc/guide/r_quickstart.hpp @@ -16,7 +16,7 @@ This quickstart guide is also available for @ref python_quickstart "Python" @section r_quickstart_install Installing mlpack binary package Installing the mlpack bindings for R is straightforward; you can just use -CRAN mirror: +CRAN: @code{.R} install.packages('mlpack') @@ -169,7 +169,9 @@ Recommendations for user 1: @section r_quickstart_nextsteps Next steps with mlpack -After working through this overview to `mlpack`'s R package, we hope you are inspired to use `mlpack`' in your data science workflow. We recommend as part of your next steps to look at more documentation for the R mlpack bindings: +After working through this overview to `mlpack`'s R package, we hope you are +inspired to use `mlpack`' in your data science workflow. We recommend as part +of your next steps to look at more documentation for the R mlpack bindings: - R mlpack binding documentation diff --git a/src/mlpack/bindings/R/CMakeLists.txt b/src/mlpack/bindings/R/CMakeLists.txt index a77c5112f64..6eb6840cceb 100644 --- a/src/mlpack/bindings/R/CMakeLists.txt +++ b/src/mlpack/bindings/R/CMakeLists.txt @@ -27,7 +27,7 @@ if (BUILD_R_BINDINGS) ## technically, I'm not sure if we even need to know! For the tests though we ## do. So it's probably a good idea to check. if (FORCE_BUILD_R_BINDINGS) - find_package(R 3.5) + find_package(R 4.0) find_r_module(roxygen2) find_r_module(Rcpp 0.12.12) find_r_module(RcppArmadillo "${RcppArmadillo_Version}") @@ -38,7 +38,7 @@ if (BUILD_R_BINDINGS) message(FATAL_ERROR "Could not Build R Bindings") endif() else () - find_package(R 3.5) + find_package(R 4.0) find_r_module(roxygen2) find_r_module(Rcpp 0.12.12) find_r_module(RcppArmadillo "${RcppArmadillo_Version}") diff --git a/src/mlpack/bindings/R/mlpack/DESCRIPTION.in b/src/mlpack/bindings/R/mlpack/DESCRIPTION.in index 3cb2cda25c4..5c141a2d44b 100644 --- a/src/mlpack/bindings/R/mlpack/DESCRIPTION.in +++ b/src/mlpack/bindings/R/mlpack/DESCRIPTION.in @@ -10,7 +10,7 @@ Description: 'mlpack' is a fast, flexible machine learning library, written SystemRequirements: A C++11 compiler. Versions 4.8.*, 4.9.* or later of GCC will be fine. License: GPL (>= 2) -Depends: R (>= 3.5.0) +Depends: R (>= 4.0.0) Imports: Rcpp (>= 0.12.12) LinkingTo: Rcpp, RcppArmadillo (>= @RcppArmadillo_Version@), diff --git a/src/mlpack/bindings/R/mlpack/src/r_util.cpp b/src/mlpack/bindings/R/mlpack/src/r_util.cpp index 2425371f580..0abe36c24a8 100644 --- a/src/mlpack/bindings/R/mlpack/src/r_util.cpp +++ b/src/mlpack/bindings/R/mlpack/src/r_util.cpp @@ -72,7 +72,7 @@ void IO_SetParamBool(const std::string& paramName, bool paramValue) // Call IO::SetParam>(). // [[Rcpp::export]] void IO_SetParamVecString(const std::string& paramName, - const std::vector& str) + const std::vector& str) { IO::GetParam>(paramName) = std::move(str); IO::SetPassed(paramName); @@ -81,7 +81,7 @@ void IO_SetParamVecString(const std::string& paramName, // Call IO::SetParam>(). // [[Rcpp::export]] void IO_SetParamVecInt(const std::string& paramName, - const std::vector& ints) + const std::vector& ints) { IO::GetParam>(paramName) = std::move(ints); IO::SetPassed(paramName); @@ -90,7 +90,7 @@ void IO_SetParamVecInt(const std::string& paramName, // Call IO::SetParam(). // [[Rcpp::export]] void IO_SetParamMat(const std::string& paramName, - const arma::mat& paramValue) + const arma::mat& paramValue) { IO::GetParam(paramName) = std::move(paramValue.t()); IO::SetPassed(paramName); @@ -99,7 +99,7 @@ void IO_SetParamMat(const std::string& paramName, // Call IO::SetParam>(). // [[Rcpp::export]] void IO_SetParamUMat(const std::string& paramName, - const arma::Mat& paramValue) + const arma::Mat& paramValue) { IO::GetParam>(paramName) = std::move(paramValue.t()); IO::SetPassed(paramName); @@ -108,7 +108,7 @@ void IO_SetParamUMat(const std::string& paramName, // Call IO::SetParam(). // [[Rcpp::export]] void IO_SetParamRow(const std::string& paramName, - const arma::rowvec& paramValue) + const arma::rowvec& paramValue) { IO::GetParam(paramName) = std::move(paramValue); IO::SetPassed(paramName); @@ -117,16 +117,16 @@ void IO_SetParamRow(const std::string& paramName, // Call IO::SetParam>(). // [[Rcpp::export]] void IO_SetParamURow(const std::string& paramName, - const arma::Row& paramValue) + const arma::Row& paramValue) { - IO::GetParam>(paramName) = std::move(paramValue); + IO::GetParam>(paramName) = std::move(paramValue - 1); IO::SetPassed(paramName); } // Call IO::SetParam(). // [[Rcpp::export]] void IO_SetParamCol(const std::string& paramName, - const arma::vec& paramValue) + const arma::vec& paramValue) { IO::GetParam(paramName) = std::move(paramValue); IO::SetPassed(paramName); @@ -135,17 +135,17 @@ void IO_SetParamCol(const std::string& paramName, // Call IO::SetParam>(). // [[Rcpp::export]] void IO_SetParamUCol(const std::string& paramName, - const arma::Col& paramValue) + const arma::Col& paramValue) { - IO::GetParam>(paramName) = std::move(paramValue); + IO::GetParam>(paramName) = std::move(paramValue - 1); IO::SetPassed(paramName); } // Call IO::SetParam>(). // [[Rcpp::export]] void IO_SetParamMatWithInfo(const std::string& paramName, - const LogicalVector& dimensions, - const arma::mat& paramValue) + const LogicalVector& dimensions, + const arma::mat& paramValue) { data::DatasetInfo d(paramValue.n_cols); for (size_t i = 0; i < d.Dimensionality(); ++i) @@ -230,7 +230,7 @@ const arma::vec IO_GetParamRow(const std::string& paramName) // [[Rcpp::export]] const arma::Col IO_GetParamURow(const std::string& paramName) { - return std::move(IO::GetParam>(paramName).t()); + return std::move(IO::GetParam>(paramName).t() + 1); } // Call IO::GetParam(). @@ -244,7 +244,7 @@ const arma::rowvec IO_GetParamCol(const std::string& paramName) // [[Rcpp::export]] const arma::Row IO_GetParamUCol(const std::string& paramName) { - return std::move(IO::GetParam>(paramName).t()); + return std::move(IO::GetParam>(paramName).t() + 1); } // Call IO::GetParam>(). diff --git a/src/mlpack/bindings/R/mlpack/tests/testthat/test-R_binding.R b/src/mlpack/bindings/R/mlpack/tests/testthat/test-R_binding.R index de944d935da..ee77ad3c336 100644 --- a/src/mlpack/bindings/R/mlpack/tests/testthat/test-R_binding.R +++ b/src/mlpack/bindings/R/mlpack/tests/testthat/test-R_binding.R @@ -132,7 +132,7 @@ test_that("TestUCol", { ucol_in=x) expect_identical(dim(output$ucol_out), as.integer(c(1, 100))) - expect_identical(output$ucol_out, 2 * x) + expect_identical(output$ucol_out, 1 + x) }) # Test a row vector input parameter. @@ -154,7 +154,7 @@ test_that("TestURow", { urow_in=x) expect_identical(dim(output$urow_out), as.integer(c(100, 1))) - expect_identical(output$urow_out, 2 * x) + expect_identical(output$urow_out, 1 + x) }) # Test that we can pass a matrix with all numeric features. diff --git a/src/mlpack/bindings/R/tests/test_r_binding_main.cpp b/src/mlpack/bindings/R/tests/test_r_binding_main.cpp index 82d0ca17f22..ecaf9f3dd9b 100644 --- a/src/mlpack/bindings/R/tests/test_r_binding_main.cpp +++ b/src/mlpack/bindings/R/tests/test_r_binding_main.cpp @@ -118,7 +118,7 @@ static void mlpackMain() { arma::Col out = move(IO::GetParam>("ucol_in")); - out *= 2; + out += 1; IO::GetParam>("ucol_out") = move(out); } @@ -135,7 +135,7 @@ static void mlpackMain() { arma::Row out = move(IO::GetParam>("urow_in")); - out *= 2; + out += 1; IO::GetParam>("urow_out") = move(out); } From 499f66581c53882fd07a99fb72de77fe26985a01 Mon Sep 17 00:00:00 2001 From: Yashwant Date: Sun, 2 Aug 2020 10:15:25 +0530 Subject: [PATCH 06/11] Add bayesian_linear_regression bindings for R. --- src/mlpack/methods/bayesian_linear_regression/CMakeLists.txt | 3 ++- .../bayesian_linear_regression_main.cpp | 4 ++-- src/mlpack/methods/rann/krann_main.cpp | 4 ++-- 3 files changed, 6 insertions(+), 5 deletions(-) diff --git a/src/mlpack/methods/bayesian_linear_regression/CMakeLists.txt b/src/mlpack/methods/bayesian_linear_regression/CMakeLists.txt index 5cdae4274dd..7ded67c3fa5 100644 --- a/src/mlpack/methods/bayesian_linear_regression/CMakeLists.txt +++ b/src/mlpack/methods/bayesian_linear_regression/CMakeLists.txt @@ -18,4 +18,5 @@ add_cli_executable(bayesian_linear_regression) add_python_binding(bayesian_linear_regression) add_julia_binding(bayesian_linear_regression) add_go_binding(bayesian_linear_regression) -add_markdown_docs(bayesian_linear_regression "cli;python;julia;go" "regression") +add_r_binding(bayesian_linear_regression) +add_markdown_docs(bayesian_linear_regression "cli;python;julia;go;r" "regression") diff --git a/src/mlpack/methods/bayesian_linear_regression/bayesian_linear_regression_main.cpp b/src/mlpack/methods/bayesian_linear_regression/bayesian_linear_regression_main.cpp index 86fc946fe2b..8dfa1127388 100644 --- a/src/mlpack/methods/bayesian_linear_regression/bayesian_linear_regression_main.cpp +++ b/src/mlpack/methods/bayesian_linear_regression/bayesian_linear_regression_main.cpp @@ -57,8 +57,8 @@ PROGRAM_INFO("BayesianLinearRegression", "responses to the test points can be saved with the " + PRINT_PARAM_STRING("predictions") + " output parameter. The " "corresponding standard deviation can be save by precising the " + - PRINT_PARAM_STRING("stds") + " parameter." - "\n\n" + PRINT_PARAM_STRING("stds") + " parameter.", + // Example. "For example, the following command trains a model on the data " + PRINT_DATASET("data") + " and responses " + PRINT_DATASET("responses") + "with center set to true and scale set to false (so, Bayesian " diff --git a/src/mlpack/methods/rann/krann_main.cpp b/src/mlpack/methods/rann/krann_main.cpp index f7b6387d195..04ac7fe898c 100644 --- a/src/mlpack/methods/rann/krann_main.cpp +++ b/src/mlpack/methods/rann/krann_main.cpp @@ -225,9 +225,9 @@ static void mlpackMain() // Apply the parameters for search. if (IO::HasParam("tau")) - rann->Tau() = tau; + rann->Tau() = IO::GetParam("tau"); if (IO::HasParam("alpha")) - rann->Alpha() = alpha; + rann->Alpha() = IO::GetParam("alpha"); if (IO::HasParam("single_sample_limit")) rann->SingleSampleLimit() = IO::GetParam("single_sample_limit"); rann->SampleAtLeaves() = IO::HasParam("sample_at_leaves"); From 056cdb2f31b76169f0530e6f2db0d1492001f30c Mon Sep 17 00:00:00 2001 From: Yashwant Singh Parihar Date: Wed, 5 Aug 2020 09:30:50 +0530 Subject: [PATCH 07/11] Apply suggestions from code review Co-authored-by: Ryan Curtin --- src/mlpack/bindings/R/mlpack/src/r_util.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/mlpack/bindings/R/mlpack/src/r_util.cpp b/src/mlpack/bindings/R/mlpack/src/r_util.cpp index 0abe36c24a8..496aace7d2f 100644 --- a/src/mlpack/bindings/R/mlpack/src/r_util.cpp +++ b/src/mlpack/bindings/R/mlpack/src/r_util.cpp @@ -119,7 +119,7 @@ void IO_SetParamRow(const std::string& paramName, void IO_SetParamURow(const std::string& paramName, const arma::Row& paramValue) { - IO::GetParam>(paramName) = std::move(paramValue - 1); + IO::GetParam>(paramName) = paramValue - 1; IO::SetPassed(paramName); } @@ -137,7 +137,7 @@ void IO_SetParamCol(const std::string& paramName, void IO_SetParamUCol(const std::string& paramName, const arma::Col& paramValue) { - IO::GetParam>(paramName) = std::move(paramValue - 1); + IO::GetParam>(paramName) = paramValue - 1; IO::SetPassed(paramName); } @@ -230,7 +230,7 @@ const arma::vec IO_GetParamRow(const std::string& paramName) // [[Rcpp::export]] const arma::Col IO_GetParamURow(const std::string& paramName) { - return std::move(IO::GetParam>(paramName).t() + 1); + return IO::GetParam>(paramName).t() + 1; } // Call IO::GetParam(). @@ -244,7 +244,7 @@ const arma::rowvec IO_GetParamCol(const std::string& paramName) // [[Rcpp::export]] const arma::Row IO_GetParamUCol(const std::string& paramName) { - return std::move(IO::GetParam>(paramName).t() + 1); + return IO::GetParam>(paramName).t() + 1; } // Call IO::GetParam>(). From 8bb399a80c45435011f2a814db58244d8b433c09 Mon Sep 17 00:00:00 2001 From: Yashwant Date: Wed, 5 Aug 2020 09:37:51 +0530 Subject: [PATCH 08/11] Resolve some final comments. --- README.md | 2 +- src/mlpack/bindings/R/default_param_impl.hpp | 6 +++--- src/mlpack/bindings/R/mlpack/DESCRIPTION.in | 2 +- src/mlpack/bindings/R/mlpack/src/Makevars | 2 +- src/mlpack/bindings/R/mlpack/src/Makevars.win | 2 +- .../bayesian_linear_regression_main.cpp | 10 +++++----- 6 files changed, 12 insertions(+), 12 deletions(-) diff --git a/README.md b/README.md index ce523ff093c..d8657d15acf 100644 --- a/README.md +++ b/README.md @@ -124,7 +124,7 @@ installed. If you would like to build the Go bindings, make sure that Go >= 1.11.0 is installed with this package: - gonum + Gonum If you would like to build the R bindings, make sure that R >= 4.0 is installed with these R packages. diff --git a/src/mlpack/bindings/R/default_param_impl.hpp b/src/mlpack/bindings/R/default_param_impl.hpp index 69b379de805..383a29d9740 100644 --- a/src/mlpack/bindings/R/default_param_impl.hpp +++ b/src/mlpack/bindings/R/default_param_impl.hpp @@ -112,17 +112,17 @@ std::string DefaultParamImpl( std::is_same::value || std::is_same::value) { - return "matrix()"; + return "matrix(c())"; } else if (std::is_same>::value || std::is_same>::value || std::is_same>::value) { - return "matrix(as.integer())"; + return "matrix(as.integer(c()))"; } else { - return "matrix()"; + return "matrix(c())"; } } diff --git a/src/mlpack/bindings/R/mlpack/DESCRIPTION.in b/src/mlpack/bindings/R/mlpack/DESCRIPTION.in index 5c141a2d44b..7a199d381de 100644 --- a/src/mlpack/bindings/R/mlpack/DESCRIPTION.in +++ b/src/mlpack/bindings/R/mlpack/DESCRIPTION.in @@ -18,7 +18,7 @@ LinkingTo: Rcpp, RcppEnsmallen (>= @RcppEnsmallen_Version@) Suggests: testthat (>= 2.1.0) URL: https://www.mlpack.org/doc/mlpack-@PACKAGE_VERSION@/r_documentation.html, - https://github.com/mlpack/mlpack-r, https://github.com/mlpack/mlpack + https://github.com/mlpack/mlpack BugReports: https://github.com/mlpack/mlpack/issues LazyData: true RoxygenNote: 7.1.0 diff --git a/src/mlpack/bindings/R/mlpack/src/Makevars b/src/mlpack/bindings/R/mlpack/src/Makevars index a8abe1dc0de..bb6a88cc846 100644 --- a/src/mlpack/bindings/R/mlpack/src/Makevars +++ b/src/mlpack/bindings/R/mlpack/src/Makevars @@ -1,3 +1,3 @@ -PKG_CXXFLAGS = -I. $(SHLIB_OPENMP_CXXFLAGS) +PKG_CXXFLAGS = -DBOOST_MATH_PROMOTE_DOUBLE_POLICY=false -I. $(SHLIB_OPENMP_CXXFLAGS) PKG_LIBS = $(SHLIB_OPENMP_CXXFLAGS) $(LAPACK_LIBS) $(BLAS_LIBS) $(FLIBS) CXX_STD = CXX11 diff --git a/src/mlpack/bindings/R/mlpack/src/Makevars.win b/src/mlpack/bindings/R/mlpack/src/Makevars.win index a8abe1dc0de..bb6a88cc846 100644 --- a/src/mlpack/bindings/R/mlpack/src/Makevars.win +++ b/src/mlpack/bindings/R/mlpack/src/Makevars.win @@ -1,3 +1,3 @@ -PKG_CXXFLAGS = -I. $(SHLIB_OPENMP_CXXFLAGS) +PKG_CXXFLAGS = -DBOOST_MATH_PROMOTE_DOUBLE_POLICY=false -I. $(SHLIB_OPENMP_CXXFLAGS) PKG_LIBS = $(SHLIB_OPENMP_CXXFLAGS) $(LAPACK_LIBS) $(BLAS_LIBS) $(FLIBS) CXX_STD = CXX11 diff --git a/src/mlpack/methods/bayesian_linear_regression/bayesian_linear_regression_main.cpp b/src/mlpack/methods/bayesian_linear_regression/bayesian_linear_regression_main.cpp index 8dfa1127388..ae367dba5ec 100644 --- a/src/mlpack/methods/bayesian_linear_regression/bayesian_linear_regression_main.cpp +++ b/src/mlpack/methods/bayesian_linear_regression/bayesian_linear_regression_main.cpp @@ -63,19 +63,19 @@ PROGRAM_INFO("BayesianLinearRegression", PRINT_DATASET("data") + " and responses " + PRINT_DATASET("responses") + "with center set to true and scale set to false (so, Bayesian " "linear regression is being solved, and then the model is saved to " + - PRINT_MODEL("bayesian_linear_regression_model") + ":" + PRINT_MODEL("blr_model") + ":" "\n\n" + PRINT_CALL("bayesian_linear_regression", "input", "data", "responses", "responses", "center", 1, "scale", 0, "output_model", - "bayesian_linear_regression_model") + + "blr_model") + "\n\n" "The following command uses the " + - PRINT_MODEL("bayesian_linear_regression_model") + " to provide predicted " + + PRINT_MODEL("blr_model") + " to provide predicted " + " responses for the data " + PRINT_DATASET("test") + " and save those " + " responses to " + PRINT_DATASET("test_predictions") + ": " "\n\n" + PRINT_CALL("bayesian_linear_regression", "input_model", - "bayesian_linear_regression_model", "test", "test", + "blr_model", "test", "test", "predictions", "test_predictions") + "\n\n" "Because the estimator computes a predictive distribution instead of " @@ -83,7 +83,7 @@ PROGRAM_INFO("BayesianLinearRegression", "allows to save the prediction uncertainties: " "\n\n" + PRINT_CALL("bayesian_linear_regression", "input_model", - "bayesian_linear_regression_model", "test", "test", + "blr_model", "test", "test", "predictions", "test_predictions", "stds", "stds"), SEE_ALSO("Bayesian Interpolation", "https://authors.library.caltech.edu/13792/1/MACnc92a.pdf"), From 48e1a05373c85753757fe41e17fccdecaa989d0a Mon Sep 17 00:00:00 2001 From: Yashwant Date: Wed, 5 Aug 2020 09:56:11 +0530 Subject: [PATCH 09/11] Add prefix variable. --- src/mlpack/bindings/R/print_R.cpp | 3 --- src/mlpack/bindings/R/print_doc.hpp | 5 ++--- src/mlpack/bindings/R/print_doc_functions_impl.hpp | 9 ++++++--- 3 files changed, 8 insertions(+), 9 deletions(-) diff --git a/src/mlpack/bindings/R/print_R.cpp b/src/mlpack/bindings/R/print_R.cpp index c90ef2fc48a..398252ec326 100644 --- a/src/mlpack/bindings/R/print_R.cpp +++ b/src/mlpack/bindings/R/print_R.cpp @@ -81,7 +81,6 @@ void PrintR(const util::ProgramDoc& programInfo, const string& opt = inputOptions[i]; util::ParamData& d = parameters.at(opt); - cout << "#' @param "; bool out = false; IO::GetSingleton().functionMap[d.tname]["PrintDoc"](d, NULL, (void*) &out); @@ -97,8 +96,6 @@ void PrintR(const util::ProgramDoc& programInfo, const string& opt = outputOptions[i]; util::ParamData& d = parameters.at(opt); - cout << "#' \\item{"; - bool out = true; IO::GetSingleton().functionMap[d.tname]["PrintDoc"](d, NULL, (void*) &out); diff --git a/src/mlpack/bindings/R/print_doc.hpp b/src/mlpack/bindings/R/print_doc.hpp index 0b9d2f0490f..e28601cac04 100644 --- a/src/mlpack/bindings/R/print_doc.hpp +++ b/src/mlpack/bindings/R/print_doc.hpp @@ -40,11 +40,10 @@ void PrintDoc(util::ParamData& d, bool out = *((bool*) output); std::ostringstream oss; - oss << d.name; if (out) - oss << "}{"; + oss << "#' \\item{" << d.name << "}{"; else - oss << " "; + oss << "#' @param " << d.name << " "; oss << d.desc.substr(0, d.desc.size() - 1); // Print a default, if possible. if (!d.required) diff --git a/src/mlpack/bindings/R/print_doc_functions_impl.hpp b/src/mlpack/bindings/R/print_doc_functions_impl.hpp index 47705c6f285..ba186fd0828 100644 --- a/src/mlpack/bindings/R/print_doc_functions_impl.hpp +++ b/src/mlpack/bindings/R/print_doc_functions_impl.hpp @@ -160,6 +160,7 @@ std::string PrintOutputOptions(const bool markdown, { // See if this is part of the program. std::string result = ""; + std::string command_prefix = "R> "; if (IO::Parameters().count(paramName) > 0) { util::ParamData& d = IO::Parameters()[paramName]; @@ -168,7 +169,7 @@ std::string PrintOutputOptions(const bool markdown, // Print a new line for the output option. std::ostringstream oss; if (markdown) - oss << "R> "; + oss << command_prefix; oss << value << " <- output$" << paramName; result = oss.str(); } @@ -240,7 +241,8 @@ std::string ProgramCall(const bool markdown, inline std::string ProgramCall(const std::string& programName) { std::ostringstream oss; - oss << "R> "; + std::string command_prefix = "R> "; + oss << command_prefix; // Determine if we have any output options. std::map& parameters = IO::Parameters(); @@ -294,7 +296,8 @@ inline std::string ProgramCall(const std::string& programName) continue; // Print a new line for the output option. - oss << std::endl << "R> " << it->second.name << " <- d$" << it->second.name; + oss << std::endl << command_prefix << it->second.name << " <- d$" + << it->second.name; } return oss.str(); From 93c553ac3968b0bc0e59966aec1949e88a6ff132 Mon Sep 17 00:00:00 2001 From: Yashwant Date: Thu, 6 Aug 2020 10:33:18 +0530 Subject: [PATCH 10/11] Change default value. --- src/mlpack/bindings/R/default_param_impl.hpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/mlpack/bindings/R/default_param_impl.hpp b/src/mlpack/bindings/R/default_param_impl.hpp index 383a29d9740..2be3f36bcd1 100644 --- a/src/mlpack/bindings/R/default_param_impl.hpp +++ b/src/mlpack/bindings/R/default_param_impl.hpp @@ -112,17 +112,17 @@ std::string DefaultParamImpl( std::is_same::value || std::is_same::value) { - return "matrix(c())"; + return "matrix(as.double(c()), 0, 0)"; } else if (std::is_same>::value || std::is_same>::value || std::is_same>::value) { - return "matrix(as.integer(c()))"; + return "matrix(as.integer(c()), 0, 0)"; } else { - return "matrix(c())"; + return "matrix(as.double(c()), 0, 0)"; } } From f11f14af9757a87eba5dd85e19e6a1c9e6d9b456 Mon Sep 17 00:00:00 2001 From: Yashwant Date: Thu, 6 Aug 2020 17:43:38 +0530 Subject: [PATCH 11/11] Update the default value as suggested. --- src/mlpack/bindings/R/default_param_impl.hpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/mlpack/bindings/R/default_param_impl.hpp b/src/mlpack/bindings/R/default_param_impl.hpp index 2be3f36bcd1..de529d011aa 100644 --- a/src/mlpack/bindings/R/default_param_impl.hpp +++ b/src/mlpack/bindings/R/default_param_impl.hpp @@ -112,17 +112,17 @@ std::string DefaultParamImpl( std::is_same::value || std::is_same::value) { - return "matrix(as.double(c()), 0, 0)"; + return "matrix(numeric(), 0, 0)"; } else if (std::is_same>::value || std::is_same>::value || std::is_same>::value) { - return "matrix(as.integer(c()), 0, 0)"; + return "matrix(integer(), 0, 0)"; } else { - return "matrix(as.double(c()), 0, 0)"; + return "matrix(numeric(), 0, 0)"; } }