001package org.biopax.paxtools.pattern.miner; 002 003import org.biopax.paxtools.controller.PathAccessor; 004import org.biopax.paxtools.model.BioPAXElement; 005import org.biopax.paxtools.model.level3.Pathway; 006import org.biopax.paxtools.model.level3.PublicationXref; 007 008import java.util.*; 009 010/** 011 * @author Ozgun Babur 012 */ 013public class SIFInteraction implements Comparable 014{ 015 public Set<BioPAXElement> sourceERs; 016 public Set<BioPAXElement> targetERs; 017 public Set<BioPAXElement> sourcePEs; 018 public Set<BioPAXElement> targetPEs; 019 public String sourceID; 020 public String targetID; 021 public SIFType type; 022 public Set<BioPAXElement> mediators; 023 024 public SIFInteraction(String sourceID, String targetID, BioPAXElement sourceER, 025 BioPAXElement targetER, SIFType type, Set<BioPAXElement> mediators, 026 Set<BioPAXElement> sourcePEs, Set<BioPAXElement> targetPEs) 027 { 028 this.sourceID = sourceID; 029 this.targetID = targetID; 030 this.sourceERs = new HashSet<BioPAXElement>(); 031 this.targetERs = new HashSet<BioPAXElement>(); 032 033 this.sourceERs.add(sourceER); 034 this.targetERs.add(targetER); 035 this.type = type; 036 037 this.mediators = mediators; 038 this.sourcePEs = sourcePEs; 039 this.targetPEs = targetPEs; 040 } 041 042 public boolean hasIDs() 043 { 044 return sourceID != null && targetID != null; 045 } 046 047 @Override 048 public int hashCode() 049 { 050 return sourceID.hashCode() + targetID.hashCode() + type.hashCode(); 051 } 052 053 @Override 054 public boolean equals(Object obj) 055 { 056 if (obj instanceof SIFInteraction) 057 { 058 SIFInteraction i = (SIFInteraction) obj; 059 060 return i.type.equals(type) && i.sourceID.equals(sourceID) && i.targetID.equals(targetID); 061 } 062 063 return false; 064 } 065 066 @Override 067 public int compareTo(Object o) 068 { 069 if (o instanceof SIFInteraction) 070 { 071 SIFInteraction i = (SIFInteraction) o; 072 073 return (sourceID + targetID + type.getTag()).compareTo( 074 i.sourceID + i.targetID + i.type.getTag()); 075 } 076 077 return 0; 078 } 079 080 /** 081 * Merges publications of the parameter equivalent sif with this one. 082 * @param equivalent the equivalent sif interaction to get its publications. 083 */ 084 public void mergeWith(SIFInteraction equivalent) 085 { 086 if (!this.equals(equivalent)) 087 throw new IllegalArgumentException("SIF interactions are not equivalent."); 088 089 sourceERs.addAll(equivalent.sourceERs); 090 targetERs.addAll(equivalent.targetERs); 091 092 sourcePEs.addAll(equivalent.sourcePEs); 093 targetPEs.addAll(equivalent.targetPEs); 094 095 if (mediators == null) mediators = equivalent.mediators; 096 else if (equivalent.mediators != null) 097 { 098 mediators.addAll(equivalent.mediators); 099 } 100 } 101 102 @Override 103 public String toString() 104 { 105 return toString(false); 106 } 107 108 public String toString(boolean withMediators) 109 { 110 String s = sourceID + "\t" + type.getTag() + "\t" + targetID; 111 112 if (withMediators) 113 { 114 String m = getMediatorsInString(); 115 if (!m.isEmpty()) s += "\t" + m; 116 } 117 118 return s; 119 } 120 121 /** 122 * Collects IDs of mediators. 123 * @return mediator IDs 124 */ 125 public List<String> getMediatorIDs() 126 { 127 List<String> ids = new ArrayList<String>(mediators.size()); 128 129 for (BioPAXElement ele : mediators) 130 { 131 ids.add(ele.getRDFId()); 132 } 133 return ids; 134 } 135 136 /** 137 * Gets the mediator IDs in a String with a space between each ID. 138 * 139 * @return mediator IDs joined with spaces. 140 */ 141 public String getMediatorsInString() 142 { 143 String m = ""; 144 for (String mid : getMediatorIDs()) 145 { 146 m+= " " + mid; 147 } 148 return m.trim(); 149 } 150 151 /** 152 * Collects PMIDs from mediators. 153 * @return PMIDs 154 */ 155 public List<String> getPubmedIDs() 156 { 157 if (mediators == null) return Collections.emptyList(); 158 159 Set<String> set = harvestPMIDs(harvestPublicationXrefs( 160 mediators.toArray(new BioPAXElement[mediators.size()]))); 161 162 List<String> list = new ArrayList<String>(set); 163 Collections.sort(list); 164 165 return list; 166 } 167 168 private static final PathAccessor xrefAcc = new PathAccessor("XReferrable/xref:PublicationXref"); 169 private static final PathAccessor evidAcc = new PathAccessor("Observable/evidence/xref:PublicationXref"); 170 171 /** 172 * Collects publication xrefs of the given elements. 173 * @param ele element array 174 * @return publication xrefs 175 */ 176 private Set<PublicationXref> harvestPublicationXrefs(BioPAXElement... ele) 177 { 178 Set<PublicationXref> set = new HashSet<PublicationXref>(); 179 180 for (Object o : xrefAcc.getValueFromBeans(Arrays.asList(ele))) 181 { 182 set.add((PublicationXref) o); 183 } 184 for (Object o : evidAcc.getValueFromBeans(Arrays.asList(ele))) 185 { 186 set.add((PublicationXref) o); 187 } 188 return set; 189 } 190 191 /** 192 * Collects PubMed IDs fromt the given publication xrefs. 193 * @param xrefs publication xrefs 194 * @return PMIDs 195 */ 196 private Set<String> harvestPMIDs(Set<PublicationXref> xrefs) 197 { 198 Set<String> set = new HashSet<String>(); 199 200 for (PublicationXref xref : xrefs) 201 { 202 if (xref.getDb() != null && xref.getDb().equalsIgnoreCase("pubmed")) 203 if (xref.getId() != null && !xref.getId().isEmpty()) 204 set.add(xref.getId()); 205 } 206 return set; 207 } 208 209 private static final PathAccessor pathwayAcc1 = new PathAccessor("Interaction/pathwayComponentOf*"); 210 private static final PathAccessor pathwayAcc2 = new PathAccessor("Interaction/stepProcessOf/pathwayOrderOf"); 211 212 /** 213 * Collects Pathway objects that the Interactions among the mediators are members. 214 * @return related pathways 215 */ 216 public Set<Pathway> getPathways() 217 { 218 Set<Pathway> set = new HashSet<Pathway>(); 219 220 for (Object o : pathwayAcc1.getValueFromBeans(mediators)) 221 { 222 set.add((Pathway) o); 223 } 224 for (Object o : pathwayAcc2.getValueFromBeans(mediators)) 225 { 226 set.add((Pathway) o); 227 } 228 229 return set; 230 } 231 232 /** 233 * Collects the names of the related pathways. 234 * @return pathway names 235 */ 236 public List<String> getPathwayNames() 237 { 238 Set<Pathway> set = getPathways(); 239 List<String> names = new ArrayList<String>(); 240 241 for (Pathway p : set) 242 { 243 String name = p.getDisplayName(); 244 if (!names.contains(name)) names.add(name); 245 } 246 247 Collections.sort(names); 248 return names; 249 } 250 251 private static final PathAccessor dataSourceAcc = new PathAccessor("Entity/dataSource/displayName"); 252 253 /** 254 * Collects data source names (Provenance display names) of mediators. 255 * @return related data sources 256 */ 257 public Set<String> getDataSources() 258 { 259 Set<String> set = new HashSet<String>(); 260 261 for (Object o : dataSourceAcc.getValueFromBeans(mediators)) 262 { 263 set.add((String) o); 264 } 265 266 return set; 267 } 268 269 private static final PathAccessor locAcc = new PathAccessor("PhysicalEntity/cellularLocation/term"); 270 271 /** 272 * Collects cellular location terms of target objects. 273 * @return cellular locations 274 */ 275 public Set<String> getCellularLocationsOfTarget() 276 { 277 return getCellularLocations(targetPEs); 278 } 279 280 /** 281 * Collects cellular location terms of source objects. 282 * @return cellular locations 283 */ 284 public Set<String> getCellularLocationsOfSource() 285 { 286 return getCellularLocations(sourcePEs); 287 } 288 289 /** 290 * Collects cellular location terms of related objects. 291 * @return cellular locations 292 */ 293 private Set<String> getCellularLocations(Set<BioPAXElement> eles) 294 { 295 Set<String> set = new HashSet<String>(); 296 297 for (Object o : locAcc.getValueFromBeans(eles)) 298 { 299 set.add((String) o); 300 } 301 302 return set; 303 } 304 305 306 307 //---- Section: Static methods ----------------------------------------------------------------| 308 309 /** 310 * Collects and sorts sourceID and targetID of the given collection of sif interactions. 311 * @param sifInts interactions to consider 312 * @param type types of interest, all types accepted if empty 313 * @return sorted source and target IDS 314 */ 315 public static List<String> getSortedGeneNames(Collection<SIFInteraction> sifInts, 316 SIFType... type) 317 { 318 Set<String> genes = new HashSet<String>(); 319 Set<SIFType> types = new HashSet<SIFType>(Arrays.asList(type)); 320 321 // collect gene names 322 323 for (SIFInteraction sifInt : sifInts) 324 { 325 if (!types.isEmpty() && !types.contains(sifInt.type)) continue; 326 327 genes.add(sifInt.sourceID); 328 genes.add(sifInt.targetID); 329 } 330 331 // sort all gene names 332 333 List<String> names = new ArrayList<String>(genes); 334 Collections.sort(names); 335 336 return names; 337 } 338 339 /** 340 * Converts the given collection of interactions into an adjacency matrix. 341 * @param sifInts interactions to consider 342 * @param type types of interest, all types accepted if empty 343 * @return the sif network as adjacency matrix 344 */ 345 public static boolean[][] convertToAdjacencyMatrix(Collection<SIFInteraction> sifInts, 346 SIFType... type) 347 { 348 Set<SIFType> types = new HashSet<SIFType>(Arrays.asList(type)); 349 350 // collect gene names 351 List<String> names = getSortedGeneNames(sifInts, type); 352 353 // record name indexes for efficient lookup 354 355 Map<String, Integer> name2ind = new HashMap<String, Integer>(); 356 int i = 0; 357 for (String name : names) 358 { 359 name2ind.put(name, i++); 360 } 361 362 // generate adjacency matrix 363 364 boolean[][] matrix = new boolean[names.size()][names.size()]; 365 for (boolean[] m : matrix) Arrays.fill(m, false); 366 367 for (SIFInteraction sifInt : sifInts) 368 { 369 if (!types.isEmpty() && !types.contains(sifInt.type)) continue; 370 371 matrix[name2ind.get(sifInt.sourceID)][name2ind.get(sifInt.targetID)] = true; 372 373 if (!sifInt.type.isDirected()) 374 { 375 matrix[name2ind.get(sifInt.targetID)][name2ind.get(sifInt.sourceID)] = true; 376 } 377 } 378 379 return matrix; 380 } 381}