Skip to main content
  • Home
  • Development
  • Documentation
  • Donate
  • Operational login
  • Browse the archive

swh logo
SoftwareHeritage
Software
Heritage
Archive
Features
  • Search

  • Downloads

  • Save code now

  • Add forge now

  • Help

https://forge.inrae.fr/genotoul-bioinfo/mixKernel.git
23 July 2025, 18:44:20 UTC
  • Code
  • Branches (7)
  • Releases (0)
  • Visits
    • Branches
    • Releases
    • HEAD
    • refs/heads/dev
    • refs/heads/master
    • refs/heads/plotind3
    • refs/tags/v0.8
    • refs/tags/v0.9
    • refs/tags/v0.9-1
    • refs/tags/v0.9-2
    No releases to show
  • 6b121a7
  • /
  • R
  • /
  • kernels.R
Raw File Download Save again
Take a new snapshot of a software origin

If the archived software origin currently browsed is not synchronized with its upstream version (for instance when new commits have been issued), you can explicitly request Software Heritage to take a new snapshot of it.

Use the form below to proceed. Once a request has been submitted and accepted, it will be processed as soon as possible. You can then check its processing state by visiting this dedicated page.
swh spinner

Processing "take a new snapshot" request ...

To reference or cite the objects present in the Software Heritage archive, permalinks based on SoftWare Hash IDentifiers (SWHIDs) must be used.
Select below a type of object currently browsed in order to display its associated SWHID and permalink.

  • content
  • directory
  • revision
  • snapshot
origin badgecontent badge
swh:1:cnt:6e9561fb41c76fb18c3a4a0801707d0f5733b006
origin badgedirectory badge
swh:1:dir:6ecf297ce903ef7e227d9cfc3b863e853aa9fa07
origin badgerevision badge
swh:1:rev:33e748dfd5e2f99f13fe3529959bada1cafc3e54
origin badgesnapshot badge
swh:1:snp:8bf247850490c25027dc03263fbade6682091726

This interface enables to generate software citations, provided that the root directory of browsed objects contains a citation.cff or codemeta.json file.
Select below a type of object currently browsed in order to generate citations for them.

  • content
  • directory
  • revision
  • snapshot
(requires biblatex-software package)
Generating citation ...
(requires biblatex-software package)
Generating citation ...
(requires biblatex-software package)
Generating citation ...
(requires biblatex-software package)
Generating citation ...
Tip revision: 33e748dfd5e2f99f13fe3529959bada1cafc3e54 authored by Nathalie Vialaneix on 25 April 2025, 08:34:15 UTC
updated mixKernel website
Tip revision: 33e748d
kernels.R
#############################################################################################################
# Author :
#   Jerome Mariette, MIAT, Universite de Toulouse, INRA 31326 Castanet-Tolosan France
#   Nathalie Vialaneix, MIAT, Universite de Toulouse, INRA 31326 Castanet-Tolosan France
#
# Copyright (C) 2017
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
#############################################################################################################

#############################################################################################################
#
#############################################################################################################

# Checks whether a matrix is a kernel
is.kernel <- function (K, test.pos.semidef = FALSE) {
  
  if (!is.matrix(K)) {
    K <- as.matrix(K)
  }
  
  if (test.pos.semidef) {
    eval <- eigen(K, only.values = TRUE, symmetric = TRUE)$values
    tolerance <- 10^(-10)
    
    if (is.complex( eval )) {
      stop("Kernel matrix has complex eigenvalues")
    }
    
    if (isSymmetric(K)) {
      return(all(eval[which(eval > tolerance)] > 0))
    } else {
      return(FALSE)
    }
  } else {
    return(isSymmetric(K))
  }
  
}


#############################################################################################################
# linear kernel
#############################################################################################################

linear <- function(X, scale = TRUE) {

  #-- checking general input parameters --#
  if (any(is.na(X))) {
    stop("'X' should not contain NAs")
  }
  if (! is.logical(scale)) {
  	stop("'scale' should be a logical value")
  }
  if (is.data.frame(X)) {
    X <- as.matrix(X)
  }
  if (! is.matrix(X) || is.character(X)) {
    stop("'X' must be a numeric matrix.", call. = FALSE)
  }
  if (any(apply(X, 1, is.infinite))) {
    stop("infinite values in 'X'.", call. = FALSE)
  }
  if (scale) {
	  X.scaled <- scale(X)
  } else {
    X.scaled <- X
  }
  
  similarities <- tcrossprod(X.scaled)
  
  return(invisible(similarities))
  
}


#############################################################################################################
# gaussian.radial.basis kernel
#############################################################################################################

gaussian.radial.basis <- function(X, scale = TRUE, sigma = 1) {
  
  #-- checking general input parameters --#
  if (any(is.na(X))) {
    stop("'X' should not contain NAs")
  }
  if (! is.logical(scale)) {
    stop("'scale' should be a logical value")
  }
  if (is.data.frame(X)) {
    X <- as.matrix(X)
  }
  if (! is.matrix(X) || is.character(X)) {
    stop("'X' must be a numeric matrix.", call. = FALSE)
  }
  if (any(apply(X, 1, is.infinite))) {
    stop("infinite values in 'X'.", call. = FALSE)
  }
  if (scale) {
    X.scaled <- scale(X)
  } else {
    X.scaled <- X
  }

  n <- dim(X.scaled)[1]
  dota <- rowSums(X.scaled * X.scaled) / 2
  
  similarities <- tcrossprod(X.scaled)
  for (i in 1:n) {
    similarities[i, ] <- exp(2 * sigma * (similarities[i,] - dota - rep(dota[i], n)))
  }
  return(invisible(similarities))
  
}


#############################################################################################################
# abundance kernel
#############################################################################################################

abundance <- function(X, method = c("bray", "manhattan", "euclidean", "canberra", 
                                    "kulczynski", "jaccard", "gower", "altGower", 
                                    "morisita", "horn",	"mountford", "raup" , 
                                    "binomial", "chao", "cao")) {

  #-- checking general input parameters --#
  method <- match.arg(method)
  if (any(is.na(X))) {
    stop("'X' should not contain NAs")
  }
  if (is.data.frame(X)) {
    X = as.matrix(X)
  }
  if (!is.matrix(X) || is.character(X)) {
    stop("'X' must be a numeric matrix.", call. = FALSE)
  }
  if (any(apply(X, 1, is.infinite))) {
    stop("infinite values in 'X'.", call. = FALSE)
  }
  
  dissimilarities <- as.matrix(vegdist(X, method=method))
    
  # convert dissimilarities into similarities
  tolerance <- 10^(-10)
  similarities <- -.5* (diag(1, nrow(dissimilarities)) - 1 / nrow(dissimilarities)) %*%
    dissimilarities %*% (diag(1, nrow(dissimilarities)) - 1 / nrow(dissimilarities))
  similarities <- round(similarities, -log10(tolerance))
  
  return(invisible(similarities))

}


#############################################################################################################
# phylogenetic kernel
#############################################################################################################

phylogenetic <- function(X, method = c("wunifrac", "unifrac"), 
                         phylogenetic.tree = NULL) {

  #-- checking general input parameters --#
  method <- match.arg(method)
  if (any(is.na(X))) {
    stop("'X' should not contain NAs")
  }
  if (is.data.frame(X)) {
    X <- as.matrix(X)
  }
  if (!is.matrix(X) || is.character(X)) {
    stop("'X' must be a numeric matrix.", call. = FALSE)
  }
  if (any(apply(X, 1, is.infinite))) {
    stop("infinite values in 'X'.", call. = FALSE)
  }
  if (is.null(phylogenetic.tree)) {
  	stop("'phylogenetic.tree' is required when computing a 'phylogenetic' kernel.", 
  	     call. = FALSE)
  }
  if (!inherits(phylogenetic.tree, "phylo")) {
  	stop("'phylogenetic.tree' should be an instance of 'phylo-class' as defined",
  	     " in the ape-package.", call. = FALSE)
  }
  
  X.OTU <- otu_table(X, taxa_are_rows=FALSE)
  X.phyloseq <- phyloseq(X.OTU, phylogenetic.tree)  
  
  dissimilarities <- as.matrix(distance(X.phyloseq, method = method))

  # convert dissimilarities into similarities
  tolerance <- 10^(-10)
  similarities <- -.5* (diag(1, nrow(dissimilarities))- 1 / nrow(dissimilarities)) %*%
    dissimilarities %*% (diag(1, nrow(dissimilarities))- 1 / nrow(dissimilarities))
  similarities <- round(similarities, -log10(tolerance))
  
  return(invisible(similarities))

}


#############################################################################################################
# poisson kernel
#############################################################################################################

null.model <- function(x, normalization = c("deseq", "mle", "quantile")) {
  
  normalization <- match.arg(normalization)
  rowsum <- rowSums(x)
  colsum <- colSums(x)
  mle <- outer(rowsum, colsum, "*") / sum(rowsum)
  
  if(normalization=="mle"){
    return(list(n = mle, sizes = rowSums(x) / sum(x)))
  } else if (normalization=="quantile"){
    # This is quantile normalization idea of Bullard et al 2010
    # quantile-normalize using 75th quantile of observed counts 
    # for each sample, excluding zero-counts
    sample.qts <- apply(x, 1, quantile, .75)
    # Don't wait to standardize by 0... min allowed is 1
    sample.qts <- pmax(sample.qts, 1) 
    sample.qts <- sample.qts / sum(sample.qts)
    fit <- outer(sample.qts, colsum, "*")
    return(list(n = fit, sizes = sample.qts))
  } else if (normalization=="deseq"){
    #Trying to implement idea from Anders and Huber Genome Biology 2010 paper.
    counts <- t(x)
    geomeans <- exp(rowMeans(log(counts)))
    sizes <- apply(counts, 2, function(cnts) median((cnts / geomeans)[geomeans > 0]))
    rawsizestr <- sizes
    sizes <- sizes / sum(sizes)
    fit <- outer(sizes, colsum, "*")
    return(list(n = fit, sizes = sizes, geomeans = geomeans, rawsizestr = rawsizestr))
  }
  
}
goodness.of.fit <- function(x, normalization) {
  ns <- null.model(x, normalization = normalization)$n
  return(sum(((x - ns)^2) / ns, na.rm = TRUE))
}
find.best.transform <- function(x) {
  alphas <- seq(.01, 1, len=50)
  gof <- rep(NA, length(alphas))
  for(alpha in alphas){
    gof[alphas==alpha] <- goodness.of.fit(x^alpha, normalization="mle")
  }
  return(alphas[which.min(abs(gof - (nrow(x) - 1) * (ncol(x) - 1)))])
}

poisson <- function(X, normalization = c("deseq", "mle", "quantile")) {
  
  beta <- 1
  normalization <- match.arg(normalization)
  alpha <- find.best.transform(X)
  X <- X^alpha
  dd <- matrix(0, nrow = nrow(X), ncol = nrow(X))
  
  for(i in 2:nrow(dd)){
    Xi <- X[i,]
    for(j in 1:(i - 1)){
      Xj <- X[j,]
      n <- null.model(X[c(i, j), ], normalization = normalization)$n
      ni <- n[1,]
      nj <- n[2,]
      di <- (Xi + beta) / (ni + beta)
      dj <- (Xj + beta) / (nj + beta)
      dd[i, j] <- sum(ni + nj - ni * di - nj * dj + Xi * log(di) + Xj * log(dj))
    }
  }
  
  dissimilarities <- as.matrix(as.dist(dd+t(dd)))
  
  # convert dissimilarities into similarities
  tolerance <- 10^(-10)
  similarities <- -.5* (diag(1, nrow(dissimilarities)) - 1 / nrow(dissimilarities)) %*%
    dissimilarities %*% (diag(1, nrow(dissimilarities)) - 1 / nrow(dissimilarities))
  similarities <- forceSymmetric(round(similarities, -log10(tolerance)))
  
  return(invisible(as.matrix(similarities)))
  
}

back to top

Software Heritage — Copyright (C) 2015–2026, The Software Heritage developers. License: GNU AGPLv3+.
The source code of Software Heritage itself is available on our development forge.
The source code files archived by Software Heritage are available under their own copyright and licenses.
Terms of use: Archive access, API— Content policy— Contact— JavaScript license information— Web API