Nothing
#-------------------------------------------------------------------------------
#' Manipulate node features in a GraphSpace object
#'
#' Utilities for extracting and adding node-associated features stored in the
#' \code{fdata} container of a \code{GraphSpace} object.
#'
#' @param x A \code{GraphSpace} object.
#'
#' @param vars Character vector specifying feature names to extract.
#' If \code{NULL}, all features are returned.
#'
#' @param as_df Logical. If \code{TRUE}, returns a \code{data.frame}.
#' Otherwise returns the original backend representation.
#'
#' @param data A matrix-like or \code{data.frame} object containing node
#' features. Rows must correspond to node identifiers.
#'
#' @return
#' \itemize{
#' \item \code{gs_fetch_features()} returns a matrix-like object or
#' \code{data.frame} containing the selected node features.
#'
#' \item \code{gs_add_features()} returns a modified
#' \code{GraphSpace} object.
#' }
#'
#' @aliases gs_fetch_features
#' @aliases gs_add_features
#' @name gs_features-utils
NULL
#-------------------------------------------------------------------------------
#' @rdname gs_features-utils
#' @export
gs_fetch_features <- function(x, vars = NULL, as_df = FALSE) {
if (!inherits(x, "GraphSpace")) {
rlang::abort("'x' must be a GraphSpace object.")
}
if (!is.null(vars)) {
.validate_gs_args("allCharacter", "vars", vars)
}
.validate_gs_args("singleLogical", "as_df", as_df)
fdata <- gs_fdata(x)
if (!inherits(fdata, "Matrix")) {
return(NULL)
}
if (!is.null(vars)) {
vars <- intersect(vars, colnames(fdata))
if (length(vars) == 0) {
return(NULL)
}
fdata <- fdata[, vars, drop = FALSE]
}
if (isTRUE(as_df)) {
fdata <- as.data.frame(fdata, drop = FALSE)
}
return(fdata)
}
#' @rdname gs_features-utils
#' @importFrom utils head
#' @export
gs_add_features <- function(x, data) {
if (!inherits(x, "GraphSpace")) {
rlang::abort("'x' must be a GraphSpace object.")
}
if (length(dim(data)) != 2) {
rlang::abort("'data' must be two-dimensional (e.g. matrix-like object).")
}
if (is.data.frame(data)) {
data <- tryCatch(
Matrix::Matrix(as.matrix(data)),
error = function(e) {
rlang::abort("'data' could not be coerced to a Matrix object.")
}
)
} else if (!inherits(data, "Matrix")) {
data <- tryCatch(
Matrix::Matrix(data),
error = function(e){
rlang::abort("'data' could not be coerced to a Matrix object.")
}
)
}
if (is.null(rownames(data))) {
rlang::abort("'data' must contain rownames matching node identifiers.")
}
if (is.null(colnames(data))) {
rlang::abort("'data' must contain feature names as column names.")
}
node_ids <- gs_nodes(x)$name
# auto-transpose if node IDs are more prevalent in columns than rows
n_col_hits <- sum(colnames(data) %in% node_ids)
n_row_hits <- sum(rownames(data) %in% node_ids)
if (n_col_hits > n_row_hits) {
rlang::inform(
"Feature matrix transposed: more node IDs found in columns than rows."
)
data <- Matrix::t(data)
}
if (!any(rownames(data) %in% node_ids)) {
rlang::abort("No GraphSpace node identifiers found in 'data'.")
}
if (anyDuplicated(rownames(data))) {
rlang::abort("'data' contains duplicated identifiers.")
}
# subset and reorder to match node order
data <- data[rownames(data) %in% node_ids, , drop = FALSE]
data <- data[match(node_ids, rownames(data)), , drop = FALSE]
# fill missing nodes with NA rows
missing <- is.na(rownames(data))
if (any(missing)) {
rlang::warn(sprintf(
"%d node(s) have no feature data and will be set to NA.", sum(missing)
))
}
rownames(data) <- node_ids
# Load fdata slot
x@fdata <- data
x@pars$signal.layer <- TRUE
return(x)
}
Any scripts or data that you put into this service are public.
Add the following code to your website.
For more information on customizing the embed code, read Embedding Snippets.