Changeset View
Changeset View
Standalone View
Standalone View
java/src/main/java/org/softwareheritage/graph/NodesFiltering.java
package org.softwareheritage.graph; | package org.softwareheritage.graph; | |||||||||
import java.util.ArrayList; | import java.util.ArrayList; | |||||||||
/** | /** | |||||||||
* <h3>NodesFiltering</h3> | ||||||||||
* <p> | ||||||||||
* class that manages the filtering of nodes that have been returned after a visit of the graph. | * class that manages the filtering of nodes that have been returned after a visit of the graph. | |||||||||
* parameterized by a string that represents either no filtering (*) or a set of node types | * parameterized by a string that represents either no filtering (*) or a set of node types. | |||||||||
* </p> | ||||||||||
vlorentz: What about overloading the constructor with a variant with no argument, instead of a magic… | ||||||||||
* | * | |||||||||
* Exemples of query : | * <ul> | |||||||||
* | * | |||||||||
* graph/visit/nodes/swh:1:rel:0000000000000000000000000000000000000010 return_types==rev will only | * <li>graph/visit/nodes/swh:1:rel:0000000000000000000000000000000000000010 return_types==rev will | |||||||||
* return 'rev' nodes. | * only return 'rev' nodes.</li> | |||||||||
* | * | |||||||||
* graph/visit/nodes/swh:1:rel:0000000000000000000000000000000000000010 return_types==rev,snp,cnt | * <li>graph/visit/nodes/swh:1:rel:0000000000000000000000000000000000000010 | |||||||||
* will only return 'rev' 'snp' 'cnt' nodes. | * return_types==rev,snp,cnt will only return 'rev' 'snp' 'cnt' nodes.</li> | |||||||||
* | * | |||||||||
* graph/visit/nodes/swh:1:rel:0000000000000000000000000000000000000010 return_types==* will return | * <li>graph/visit/nodes/swh:1:rel:0000000000000000000000000000000000000010 return_types==* will | |||||||||
* all the nodes bec. | * return all the nodes.</li> | |||||||||
* </ul> | ||||||||||
* | ||||||||||
* How to use NodesFiltering : | ||||||||||
* | ||||||||||
* <pre> | ||||||||||
* {@code | ||||||||||
Not Done Inline ActionsWouldn't this work? for (String type : types) { restrictedNodesTypes.add(Node.Type.fromStr(type)); } or even this? Collections.addAll(restrictedNodesTypes, types) vlorentz: Wouldn't this work?
```
for (String type : types) {… | ||||||||||
* Long id1 = .... // graph.getNodeType(id1) == CNT | ||||||||||
* Long id2 = .... // graph.getNodeType(id2) == SNP | ||||||||||
* Long id3 = .... // graph.getNodeType(id3) == ORI | ||||||||||
* ArrayList<Long> nodeIds = nez ArrayList<Long>(); | ||||||||||
* nodeIds.add(id1); nodeIds.add(id2); nodeIds.add(id3); | ||||||||||
* | ||||||||||
* NodeFiltering nds = new NodesFiltering("snp,ori"); // we allow only snp node types to be shown | ||||||||||
* System.out.println(nds.filterByNodeTypes(nodeIds,graph)); // will print id2, id3 | ||||||||||
* | ||||||||||
* nds = NodesFiltering("*"); | ||||||||||
* System.out.println(nds.filterByNodeTypes(nodeIds,graph)); // will print id1, id2 id3 | ||||||||||
* | ||||||||||
* } | ||||||||||
* </pre> | ||||||||||
Not Done Inline ActionsDoesn't this return a value *and* modify the argument? this could be confusing to use. What about creating a new ArrayList and adding matching elements to it? vlorentz: Doesn't this return a value *and* modify the argument? this could be confusing to use.
What… | ||||||||||
Not Done Inline ActionsAnd I'm not very familiar with Java, but isn't ArrayList backed by a single dynamic array? This means every remove operation needs to copy all elements on the right, so filterByNodeTypes runs in quadratic time. vlorentz: And I'm not very familiar with Java, but isn't ArrayList backed by a single dynamic array? This… | ||||||||||
*/ | */ | |||||||||
public class NodesFiltering { | public class NodesFiltering { | |||||||||
boolean restricted; | boolean restricted; | |||||||||
ArrayList<Node.Type> allowedNodesTypes; | ArrayList<Node.Type> allowedNodesTypes; | |||||||||
/** | /** | |||||||||
* Default constructor, in order to handle the * case (all types of nodes are allowed to be | * Default constructor, in order to handle the * case (all types of nodes are allowed to be | |||||||||
* returned) | * returned). allowedNodesTypes will contains [SNP,CNT....] all types of nodes. | |||||||||
* | * | |||||||||
*/ | */ | |||||||||
public NodesFiltering() { | public NodesFiltering() { | |||||||||
restricted = false; | restricted = false; | |||||||||
allowedNodesTypes = Node.Type.parse("*"); | allowedNodesTypes = Node.Type.parse("*"); | |||||||||
} | } | |||||||||
/** | /** | |||||||||
* Constructor | ||||||||||
* | ||||||||||
* @param strTypes a formatted string describing the types of nodes we want to allow to be shown. | ||||||||||
* | ||||||||||
* NodesFilterind("cnt,snp") will set allowedNodesTypes to [CNT,SNP] | ||||||||||
* | ||||||||||
*/ | */ | |||||||||
public NodesFiltering(String strTypes) { | public NodesFiltering(String strTypes) { | |||||||||
restricted = true; | restricted = true; | |||||||||
allowedNodesTypes = new ArrayList<Node.Type>(); | allowedNodesTypes = new ArrayList<Node.Type>(); | |||||||||
String[] types = strTypes.split(","); | String[] types = strTypes.split(","); | |||||||||
for (String type : types) { | for (String type : types) { | |||||||||
allowedNodesTypes.add(Node.Type.fromStr(type)); | allowedNodesTypes.add(Node.Type.fromStr(type)); | |||||||||
} | } | |||||||||
} | } | |||||||||
/** | ||||||||||
* Check if the type given in parameter is in the list of allowed types. | ||||||||||
* | ||||||||||
* @param typ the type of the node. | ||||||||||
*/ | ||||||||||
public boolean typeIsAllowed(Node.Type typ) { | public boolean typeIsAllowed(Node.Type typ) { | |||||||||
return this.allowedNodesTypes.contains(typ); | return this.allowedNodesTypes.contains(typ); | |||||||||
} | } | |||||||||
/** | /** | |||||||||
* <p> | ||||||||||
* the function that filters the nodes returned, we browse the list of nodes found after a visit and | * the function that filters the nodes returned, we browse the list of nodes found after a visit and | |||||||||
* we create a new list with only the nodes that have a type that is contained in the list of | * we create a new list with only the nodes that have a type that is contained in the list of | |||||||||
* allowed types (allowedNodesTypes) | * allowed types (allowedNodesTypes) | |||||||||
Not Done Inline Actions
vlorentz: | ||||||||||
* </p> | ||||||||||
* | ||||||||||
* @param nodeIds the nodes founded during the visit | ||||||||||
* @param g the graph in order to find the types of nodes from their id in nodeIds | ||||||||||
* @return a new list with the id of node which have a type in allowedTypes | ||||||||||
* | ||||||||||
* | * | |||||||||
* We need the graph in order to find the types of nodes. | ||||||||||
*/ | */ | |||||||||
public ArrayList<Long> filterByNodeTypes(ArrayList<Long> nodeIds, Graph g) { | public ArrayList<Long> filterByNodeTypes(ArrayList<Long> nodeIds, Graph g) { | |||||||||
ArrayList<Long> filteredNodes = new ArrayList<Long>(); | ArrayList<Long> filteredNodes = new ArrayList<Long>(); | |||||||||
for (Long node : nodeIds) { | for (Long node : nodeIds) { | |||||||||
if (this.typeIsAllowed(g.getNodeType(node))) { | if (this.typeIsAllowed(g.getNodeType(node))) { | |||||||||
filteredNodes.add(node); | filteredNodes.add(node); | |||||||||
} | } | |||||||||
} | } | |||||||||
return filteredNodes; | return filteredNodes; | |||||||||
} | } | |||||||||
} | } |
What about overloading the constructor with a variant with no argument, instead of a magic value *?