UCLouvain-CBIO / scp

Single cell proteomics data processing
https://uclouvain-cbio.github.io/scp/index.html
19 stars 2 forks source link

scplainer: Component analysis and reducedDims #52

Closed lgatto closed 4 months ago

lgatto commented 6 months ago

@cvanderaa - what about adding the outputs of scpComponentAnalysis() to the reducedDims slot?

Going through the woo2022_macrophage scplainer vignette, the code chunk computing the TSNE was rather convoluted (lapply over caRes elements), when it really should only be a matter of calling scater::plotTSNE(sce). Not sure if the cell PC scores and feature eigenvectors shoud/can go in there, but we should at least have a helper fonction to coerce and populate the reducedDims slot.

lgatto commented 6 months ago

Here's an example implementation:

asReducedDims <- function(x) {
    .getPCs <- function(x) {
        pcs <- x[, grep("^PC", colnames(x))]
        res <- as.matrix(pcs)
        attr(res, "proportionVariance") <-
            metadata(x)$proportionVariance
        res
    }
    List(lapply(x, .getPCs))
}

And then, using data such as this one

caRes <- scpComponentAnalysis(
    sce, ncomp = 10, method = "APCA", effect = "Treatment",
    maxiter = 200)
caResCells <- caRes$bySample

Application:

> reducedDims(sce)
List of length 0
names(0): 
> reducedDims(sce) <- asReducedDims(caResCells)
> sce <- runTSNE(sce, dimred = "APCA_Treatment")
> reducedDims(sce)
List of length 4
names(4): unmodelled residuals APCA_Treatment TSNE
> plotReducedDim(sce, dimred = "APCA_Treatment", colour_by = "Treatment")
> plotTSNE(sce, colour_by = "Treatment")

plot

cvanderaa commented 6 months ago

Ah yes! I do like your suggestion and example.

In your first message, I was afraid you wanted to stored the output from scpComponentAnalysis() directly into the sce, which I think shoud not be done.

I find the asReducedDims() function elegant and clean. Although I'm not sure your line

reducedDims(sce) <- asReducedDims(caResCells)

is ideal since any existing matrix in reducedDims(sce) would get erased. Maybe having

addReducedDims <- function(sce, x) {
    .getPCs <- function(x) {
        pcs <- x[, grep("^PC", colnames(x))]
        res <- as.matrix(pcs)
        attr(res, "proportionVariance") <-
            metadata(x)$proportionVariance
        res
    }
    pcList <- List(lapply(x, .getPCs))
    reducedDims(sce) <- c(reducedDims(sce), pcList)
   sce
}
sce <- addReducedDims(sce, caResCells)
lgatto commented 6 months ago

Here's a documented implementation to be added to the scplainer code base.

##' @title Add scplainer Component Analysis Results
##'
##' @description The function will add the component results computed
##'     by [scpComponentAnalysis()] to a `SingleCellExperiment`'s
##'     `reducedDims` slot, to all using the many `scater` functions,
##'     such as [scater::plotReducedDim()], [plotTNSE()], ...
##'
##' @param sce An instance of class [SingleCellExperiment].
##'
##' @param x A `List` of `DataFrames` containing principal components,
##'     as procudes by [scpComponentAnalysis()].
##'
##' @return A `SingleCellExperiment` with updated `reducedDims`.
##'
##' @author Laurent Gatto and Christophe Vanderaa
##'
##' @examples
##'
##' library("scater")
##' data("leduc_minimal")
##' leduc_minimal$cell <- rownames(colData(leduc_minimal))
##' pcs <- scpComponentAnalysis(
##'    leduc_minimal, method = "ASCA",
##'    effects = "SampleType")$bySample
##'
##' reducedDims(leduc_minimal)
##' leduc_minimal <- addReducedDims(leduc_minimal, pcs)
##' reducedDims(leduc_minimal)
##' plotReducedDim(leduc_minimal, dimred = "ASCA_SampleType",
##'                colour_by = "SampleType")
##' leduc_minimal <- runTSNE(leduc_minimal, dimred = "ASCA_SampleType")
##' plotTSNE(leduc_minimal, colour_by = "SampleType")
addReducedDims <- function(sce, x) {
    .getPCs <- function(x) {
        pcs <- x[, grep("^PC", colnames(x))]
        res <- as.matrix(pcs)
        attr(res, "proportionVariance") <-
            metadata(x)$proportionVariance
        res
    }
    pcList <- List(lapply(x, .getPCs))
    reducedDims(sce) <- c(reducedDims(sce), pcList)
    sce
}
lgatto commented 5 months ago

Added with 01afadd98cafdc8fb44d033dd2273d11c508a3d9

lgatto commented 4 months ago

@cvanderaa - I think this function should be mentioned or illustrated in the modelling vignette, otherwise, users won't learn about it. Could you add this?

cvanderaa commented 4 months ago

Yes I'll work on it!