/* * Copyright (c) 2010 The Jackson Laboratory * * This 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 3 of the License, or * (at your option) any later version. * * This software 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 software. If not, see <http://www.gnu.org/licenses/>. */ package org.jax.maanova.fit; import java.util.ArrayList; import java.util.Collections; import java.util.List; import java.util.logging.Level; import java.util.logging.Logger; import org.jax.maanova.madata.MicroarrayExperiment; import org.jax.r.RCommandParameter; import org.jax.r.RMethodInvocationCommand; import org.jax.r.RSyntaxException; import org.jax.r.RUtilities; import org.jax.r.jriutilities.JRIUtilityFunctions; import org.jax.r.jriutilities.RInterface; import org.jax.r.jriutilities.RObject; import org.jax.r.jriutilities.SilentRCommand; import org.rosuda.JRI.REXP; /** * This object is an encapsulation of the return result of an R/maanova * {@code fitmaanova(...)} call. * @author <A HREF="mailto:keith.sheppard@jax.org">Keith Sheppard</A> */ public class FitMaanovaResult extends RObject { /** * our logger */ private static final Logger LOG = Logger.getLogger( FitMaanovaResult.class.getName()); /** * This is the name that R/maanova assigns to the underlying R type. */ public static final String R_CLASS_STRING = "maanova"; /** * The suffix used for the named item that holds the term levels */ private static final String TERM_NAME_SUFFIX = ".level"; private static final String VARIANCE_LEVELS = "S2.level"; private static final String Y_HAT_COMPONENT = "$yhat"; private static final String PROBESET_ID_COMPONENT = "$probeid"; private final MicroarrayExperiment parentExperiment; /** * Constructor * @param parentExperiment * the experiment that this belongs to * @param accessorExpressionString * the accessor expression that you use in R to get * to the */ public FitMaanovaResult( MicroarrayExperiment parentExperiment, String accessorExpressionString) { super(parentExperiment.getRInterface(), accessorExpressionString); this.parentExperiment = parentExperiment; } /** * Getter for the experiment that this fit belongs to * @return the parent */ public MicroarrayExperiment getParentExperiment() { return this.parentExperiment; } /** * Getter for the fit term names * @return * get the names */ public List<String> getFitTermNames() { String[] allNames = JRIUtilityFunctions.getNames(this); List<String> fitTermNames = new ArrayList<String>(); for(String name: allNames) { if(name.endsWith(TERM_NAME_SUFFIX) && !name.equals(VARIANCE_LEVELS)) { // add the term name to the list after we pull out the suffix String termName = name.substring( 0, name.length() - TERM_NAME_SUFFIX.length()); fitTermNames.add(termName); } } return fitTermNames; } /** * Get the levels available for the given term name * @param term * the term that we're getting the levels for * @return * the level strings */ public String[] getFitTermLevels(String term) { try { // first create term identifier safely and then get the values String termId = this.getAccessorExpressionString() + "$" + RUtilities.quoteIdentifierIfRequired(term + TERM_NAME_SUFFIX); RMethodInvocationCommand termsAsChar = new RMethodInvocationCommand( "as.character", Collections.singletonList(new RCommandParameter(termId))); REXP termRExpression = this.getRInterface().evaluateCommand( new SilentRCommand(termsAsChar)); // TODO confirm that this will always be a vector of strings and not // a vector of factors String[] termLevels = termRExpression.asStringArray(); return termLevels; } catch(RSyntaxException ex) { LOG.log(Level.SEVERE, "failed to get fit term levels", ex); return null; } } /** * Get the yHat values for the given dye * @param dyeIndex the 0-based dye index * @param arrayIndex the 0-based array index * @return the yHat's */ public Double[] getYHatValues(int dyeIndex, int arrayIndex) { int dyeCount = this.getParentExperiment().getDyeCount(); int colIndex = arrayIndex * dyeCount + dyeIndex; REXP yHatsExpr = this.getRInterface().evaluateCommand(new SilentRCommand( RUtilities.columnIndexExpression( this.getAccessorExpressionString() + Y_HAT_COMPONENT, colIndex))); return JRIUtilityFunctions.extractDoubleValues(yHatsExpr); } /** * Getter for the probeset ID strings * @return * the probeset ID strings */ public String[] getProbesetIds() { SilentRCommand probesetIdsCommand = new SilentRCommand( this.probesetIdAccessor()); REXP probesetIdsExpr = this.getRInterface().evaluateCommand( probesetIdsCommand); return probesetIdsExpr.asStringArray(); } /** * Get the probeset ID at the given index * @param probesetIndex * the index * @return the probeset ID string */ public String getProbesetId(int probesetIndex) { SilentRCommand probesetIdCommand = new SilentRCommand( RUtilities.indexExpression( this.probesetIdAccessor(), probesetIndex)); REXP probesetIdsExpr = this.getRInterface().evaluateCommand( probesetIdCommand); return probesetIdsExpr.asString(); } private String probesetIdAccessor() { // TODO correct this in R/maanova // the as.character is necessary because read.madata sometimes // results in integer rather than string data return "as.character(" + this.getAccessorExpressionString() + PROBESET_ID_COMPONENT + ")"; } /** * Get all of the top-level R objects whose class is {@value #R_CLASS_STRING} * @param rInterface * the R interface to extract the objects from * @return * the R objects of type {@value #R_CLASS_STRING} */ public static List<RObject> getAllFitRObjects(RInterface rInterface) { List<RObject> fitIdentifiers = JRIUtilityFunctions.getTopLevelObjectsOfType( rInterface, R_CLASS_STRING); if(LOG.isLoggable(Level.FINEST)) { StringBuffer message = new StringBuffer( "detected fit data objects:"); for(RObject currFitId: fitIdentifiers) { message.append(" " + currFitId.getAccessorExpressionString()); } LOG.finest(message.toString()); } return fitIdentifiers; } /** * delete this fit result */ public void delete() { RMethodInvocationCommand rmMethod = new RMethodInvocationCommand( "rm", new RCommandParameter(this.getAccessorExpressionString())); this.getRInterface().evaluateCommandNoReturn(rmMethod); } }