diff --git a/src/main/java/net/onrc/onos/ofcontroller/topology/Topology.java b/src/main/java/net/onrc/onos/ofcontroller/topology/Topology.java
index 1674cf0..9fca86a 100644
--- a/src/main/java/net/onrc/onos/ofcontroller/topology/Topology.java
+++ b/src/main/java/net/onrc/onos/ofcontroller/topology/Topology.java
@@ -1,6 +1,5 @@
 package net.onrc.onos.ofcontroller.topology;
 
-import java.util.ArrayList;
 import java.util.List;
 import java.util.LinkedList;
 import java.util.Map;
@@ -12,7 +11,6 @@
 import net.onrc.onos.ofcontroller.core.INetMapTopologyObjects.ISwitchObject;
 import net.onrc.onos.ofcontroller.core.ISwitchStorage.SwitchState;
 
-import org.apache.commons.lang.StringUtils;
 import org.openflow.util.HexString;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
@@ -195,7 +193,10 @@
  */
 public class Topology {
     private final static Logger log = LoggerFactory.getLogger(Topology.class);
-
+    
+    // flag to use optimized readFromDatabase() method.
+    private static final boolean enableOptimizedRead = false;
+    
     private Map<Long, Node> nodesMap;	// The dpid->Node mapping
 
     /**
@@ -392,289 +393,173 @@
      * @param dbHandler the Graph Database handler to use.
      */
     public void readFromDatabase(DBOperation dbHandler) {
-		//
-		// Fetch the relevant info from the Switch and Port vertices
-		// from the Titan Graph.
-		//
-    	nodesMap.clear();
+    	if (enableOptimizedRead) {
+    		readFromDatabaseBodyOptimized(dbHandler);
+    	} else {
+    		readFromDatabaseBody(dbHandler);
+    	}
 
-        // Load all switches into Map
-        Iterable<ISwitchObject> switches = dbHandler.getAllSwitches();
-        for (ISwitchObject switchObj : switches) {
-        	// Ignore inactive ports
-            if (!switchObj.getState().equals(SwitchState.ACTIVE.toString())) {
-            	continue;
-            }
-            Vertex nodeVertex = switchObj.asVertex();
-            //
-            // The Switch info
-            //
-            String nodeDpid = nodeVertex.getProperty("dpid").toString();
-            long nodeId = HexString.toLong(nodeDpid);
-            addNode(nodeId);
-        }
-
-        //
-        // Get All Ports
-        //
-        Iterable<IPortObject> ports = dbHandler.getAllPorts(); //TODO: Add to DB operations
-        for (IPortObject myPortObj : ports) {
-            Vertex myPortVertex = myPortObj.asVertex();
-
-            // Ignore inactive ports
-            if (! myPortVertex.getProperty("state").toString().equals("ACTIVE")) {
-            	continue;
-            }
-
-            short myPort = 0;
-            String idStr = myPortObj.getPortId();
-            String[] splitter = idStr.split(IDBOperation.PORT_ID_DELIM);
-            if (splitter.length != 2) {
-            	log.error("Invalid port_id : {}", idStr);
-            	continue;
-            }
-            String myDpid = splitter[0];
-            myPort = Short.parseShort(splitter[1]);
-            long myId = HexString.toLong(myDpid);
-            Node me = nodesMap.get(myId);
-
-            if (me == null) {
-                // cannot proceed ports and switches are out of sync
-                //TODO: Restart the whole read
-                continue;
-            }
-
-            if (me.getPort(myPort) == null) {
-            	me.addPort(myPort);
-            } else if (me.getLink(myPort) != null) {
-                // Link already added..probably by neighbor
-                continue;
-            }
-
-            //
-            // The neighbor Port info
-            //
-            for (Vertex neighborPortVertex : myPortVertex.getVertices(Direction.OUT, "link")) {
-//            	log.debug("state : {}", neighborPortVertex.getProperty("state"));
-//            	log.debug("port id : {}", neighborPortVertex.getProperty("port_id"));
-                // Ignore inactive ports
-                if (! neighborPortVertex.getProperty("state").toString().equals("ACTIVE")) {
-                	continue;
-                }
-                int neighborPort = 0;
-                idStr = neighborPortVertex.getProperty("port_id").toString();
-                splitter = idStr.split(IDBOperation.PORT_ID_DELIM);
-                if (splitter.length != 2) {
-                	log.error("Invalid port_id : {}", idStr);
-                	continue;
-                }
-                String neighborDpid = splitter[0];
-                neighborPort = Short.parseShort(splitter[1]);
-                long neighborId = HexString.toLong(neighborDpid);
-                Node neighbor = nodesMap.get(neighborId);
-//                log.debug("dpid {},{}  port {}", neighborDpid, neighborId, neighborPort);
-                if (neighbor == null) {
-                	continue;
-                }
-                me.addLink(myPort, neighbor, neighborPort);
-            }
-        }
-        dbHandler.commit();
     }
 
-
-    // Only for debug use
-    List<Long> logGetSw = new ArrayList<Long>(100);
-    List<Long> logGetPt = new ArrayList<Long>(100);
-    List<Long> logAddSw = new ArrayList<Long>(100);
-    List<Long> logAddPt = new ArrayList<Long>(100);
-    List<Long> logAddLk = new ArrayList<Long>(100);
-    List<Long> logCommit = new ArrayList<Long>(100);
-    List<Integer> logGetVertices = new ArrayList<Integer>(100);
-    List<Integer> logGetProperty = new ArrayList<Integer>(100);
-       public void readFromDatabaseBreakdown(DBOperation dbHandler) {
-    	int getVerticesCount = 0;
-    	int getPropertyCount = 0;
-    	int getVCount_sw = 0;
-    	int getVCount_pt = 0;
-    	int getVCount_lk = 0;
-    	int getPCount_sw = 0;
-    	int getPCount_pt = 0;
-    	int getPCount_lk = 0;
-
-		//
-		// Fetch the relevant info from the Switch and Port vertices
-		// from the Titan Graph.
-		//
+    private void readFromDatabaseBody(DBOperation dbHandler) {
+    	//
+    	// Fetch the relevant info from the Switch and Port vertices
+    	// from the Titan Graph.
+    	//
 
     	nodesMap.clear();
-    	long t1 = System.nanoTime();
+    	Iterable<ISwitchObject> activeSwitches = dbHandler.getActiveSwitches();
+    	for (ISwitchObject switchObj : activeSwitches) {
+    	    Vertex nodeVertex = switchObj.asVertex();
+    	    //
+    	    // The Switch info
+    	    //
+    	    String nodeDpid = nodeVertex.getProperty("dpid").toString();
+    	    long nodeId = HexString.toLong(nodeDpid);
+    	    Node me = nodesMap.get(nodeId);
+    	    if (me == null)
+    		me = addNode(nodeId);
 
-        // Load all switches into Map
-        Iterable<ISwitchObject> switches = dbHandler.getAllSwitches();
+    	    //
+    	    // The local Port info
+    	    //
+    	    for (Vertex myPortVertex : nodeVertex.getVertices(Direction.OUT, "on")) {
+    		// Ignore inactive ports
+    		if (! myPortVertex.getProperty("state").toString().equals("ACTIVE"))
+    		    continue;
 
-        long t2 = System.nanoTime();
+    		int myPort = 0;
+    		Object obj = myPortVertex.getProperty("number");
+    		if (obj instanceof Short) {
+    		    myPort = (Short)obj;
+    		} else if (obj instanceof Integer) {
+    		    myPort = (Integer)obj;
+    		}
+    		me.addPort(myPort);
 
-        long t_addSw = 0;
-        for (ISwitchObject switchObj : switches) {
-            long t3 = System.nanoTime();
-            long t4;
+    		for (Vertex neighborPortVertex : myPortVertex.getVertices(Direction.OUT, "link")) {
+    		    // Ignore inactive ports
+    		    if (! neighborPortVertex.getProperty("state").toString().equals("ACTIVE")) {
+    		    	continue;
+    		    }
 
-        	// Ignore inactive ports
-            ++getPropertyCount;
-            ++getPCount_sw;
-            if (!switchObj.getState().equals(SwitchState.ACTIVE.toString())) {
-                t4 = System.nanoTime();
-                t_addSw += t4 - t3;
-            	continue;
-            }
-            Vertex nodeVertex = switchObj.asVertex();
-            //
-            // The Switch info
-            //
-            ++getPropertyCount;
-            ++getPCount_sw;
-            String nodeDpid = nodeVertex.getProperty("dpid").toString();
-            long nodeId = HexString.toLong(nodeDpid);
-            addNode(nodeId);
-            t4 = System.nanoTime();
-            t_addSw += t4 - t3;
-        }
+    		    int neighborPort = 0;
+    		    obj = neighborPortVertex.getProperty("number");
+    		    if (obj instanceof Short) {
+    			neighborPort = (Short)obj;
+    		    } else if (obj instanceof Integer) {
+    			neighborPort = (Integer)obj;
+    		    }
+    		    //
+    		    // The neighbor Switch info
+    		    //
+    		    for (Vertex neighborVertex : neighborPortVertex.getVertices(Direction.IN, "on")) {
+    			// Ignore inactive switches
+    			String state = neighborVertex.getProperty("state").toString();
+    			if (! state.equals(SwitchState.ACTIVE.toString()))
+    			    continue;
 
-        long t5 = System.nanoTime();
-        //
-        // Get All Ports
-        //
-        Iterable<IPortObject> ports = dbHandler.getAllPorts(); //TODO: Add to DB operations
-
-        long t6 = System.nanoTime();
-        long t_addPort = 0;
-        long t_addLink = 0;
-
-        for (IPortObject myPortObj : ports) {
-            long t7 = System.nanoTime();
-            long t8;
-            Vertex myPortVertex = myPortObj.asVertex();
-
-            // Ignore inactive ports
-            ++getPropertyCount;
-            ++getPCount_pt;
-            if (! myPortVertex.getProperty("state").toString().equals("ACTIVE")) {
-                t8 = System.nanoTime();
-                t_addPort += t8 - t7;
-            	continue;
-            }
-
-            short myPort = 0;
-            ++getPropertyCount;
-            ++getPCount_pt;
-            String idStr = myPortObj.getPortId();
-            String[] splitter = idStr.split(IDBOperation.PORT_ID_DELIM);
-            if (splitter.length != 2) {
-            	log.error("Invalid port_id : {}", idStr);
-                t8 = System.nanoTime();
-                t_addPort += t8 - t7;
-            	continue;
-            }
-            String myDpid = splitter[0];
-            myPort = Short.parseShort(splitter[1]);
-            long myId = HexString.toLong(myDpid);
-            Node me = nodesMap.get(myId);
-
-            if (me == null) {
-                // cannot proceed ports and switches are out of sync
-                //TODO: Restart the whole read
-                t8 = System.nanoTime();
-                t_addPort += t8 - t7;
-                continue;
-            }
-
-            if (me.getPort(myPort) == null) {
-            	me.addPort(myPort);
-            } else if (me.getLink(myPort) != null) {
-                // Link already added..probably by neighbor
-                t8 = System.nanoTime();
-                t_addPort += t8 - t7;
-                continue;
-            }
-            t8 = System.nanoTime();
-            t_addPort += t8 - t7;
-
-            //
-            // The neighbor Port info
-            //
-            ++getVerticesCount;
-            ++getVCount_pt;
-            for (Vertex neighborPortVertex : myPortVertex.getVertices(Direction.OUT, "link")) {
-//            	log.debug("state : {}", neighborPortVertex.getProperty("state"));
-//            	log.debug("port id : {}", neighborPortVertex.getProperty("port_id"));
-
-                long t9 = System.nanoTime();
-                long t10;
-
-                // Ignore inactive ports
-                ++getPropertyCount;
-                ++getPCount_lk;
-                if (! neighborPortVertex.getProperty("state").toString().equals("ACTIVE")) {
-                    t10 = System.nanoTime();
-                    t_addLink += t10 - t9;
-                	continue;
-                }
-                int neighborPort = 0;
-                ++getPropertyCount;
-                ++getPCount_lk;
-                idStr = neighborPortVertex.getProperty("port_id").toString();
-                splitter = idStr.split(IDBOperation.PORT_ID_DELIM);
-                if (splitter.length != 2) {
-                	log.error("Invalid port_id : {}", idStr);
-                    t10 = System.nanoTime();
-                    t_addLink += t10 - t9;
-                	continue;
-                }
-                String neighborDpid = splitter[0];
-                neighborPort = Short.parseShort(splitter[1]);
-                long neighborId = HexString.toLong(neighborDpid);
-                Node neighbor = nodesMap.get(neighborId);
-//                log.debug("dpid {},{}  port {}", neighborDpid, neighborId, neighborPort);
-                if (neighbor == null) {
-                    t10 = System.nanoTime();
-                    t_addLink += t10 - t9;
-                	continue;
-                }
-                me.addLink(myPort, neighbor, neighborPort);
-
-                t10 = System.nanoTime();
-                t_addLink += t10 - t9;
-            }
-        }
-        long t11 = System.nanoTime();
-        dbHandler.commit();
-        long t12 = System.nanoTime();
-
-        logGetSw.add((t2-t1)/1000);
-        logGetPt.add((t6-t5)/1000);
-        logAddSw.add(t_addSw/1000);
-        logAddPt.add(t_addPort/1000);
-        logAddLk.add(t_addLink/1000);
-        logCommit.add((t12-t11)/1000);
-        logGetVertices.add(getVerticesCount);
-        logGetProperty.add(getPropertyCount);
-        log.debug("getVertices[N({}),P({}),L({})] getProperty[N({}),P({}),L({})]",
-        		new Object[]{getVCount_sw,getVCount_pt,getVCount_lk,
-        		getPCount_sw,getPCount_pt,getPCount_lk});
+    			String neighborDpid = neighborVertex.getProperty("dpid").toString();
+    			long neighborId = HexString.toLong(neighborDpid);
+    			Node neighbor = nodesMap.get(neighborId);
+    			if (neighbor == null)
+    			    neighbor = addNode(neighborId);
+    			neighbor.addPort(neighborPort);
+    			me.addLink(myPort, neighbor, neighborPort);
+    		    }
+    		}
+    	    }
+    	}
+    	dbHandler.commit();
     }
 
-    public void printMeasuredLog() {
-    	log.debug("getsw: {}", StringUtils.join(logGetSw, ","));
-    	log.debug("getpt: {}", StringUtils.join(logGetPt, ","));
-    	log.debug("addsw: {}", StringUtils.join(logAddSw, ","));
-    	log.debug("addpt: {}", StringUtils.join(logAddPt, ","));
-    	log.debug("addlk: {}", StringUtils.join(logAddLk, ","));
-    	log.debug("commit: {}", StringUtils.join(logCommit, ","));
-    	log.debug("getvertices: {}", StringUtils.join(logGetVertices, ","));
-    	log.debug("getproperty: {}", StringUtils.join(logGetProperty, ","));
+    private void readFromDatabaseBodyOptimized(DBOperation dbHandler) {
+	    nodesMap.clear();
+		    
+		// Load all switches into Map
+		Iterable<ISwitchObject> switches = dbHandler.getAllSwitches();
+		for (ISwitchObject switchObj : switches) {
+		        // Ignore inactive ports
+		    if (!switchObj.getState().equals(SwitchState.ACTIVE.toString())) {
+	            continue;
+		    }
+		    Vertex nodeVertex = switchObj.asVertex();
+		    //
+		    // The Switch info
+		    //
+		    String nodeDpid = nodeVertex.getProperty("dpid").toString();
+		    long nodeId = HexString.toLong(nodeDpid);
+		    addNode(nodeId);
+		}
+		
+		//
+		// Get All Ports
+		//
+		Iterable<IPortObject> ports = dbHandler.getAllPorts(); //TODO: Add to DB operations
+		for (IPortObject myPortObj : ports) {
+		    Vertex myPortVertex = myPortObj.asVertex();
+		    
+		    // Ignore inactive ports
+		    if (! myPortVertex.getProperty("state").toString().equals("ACTIVE")) {
+	            continue;
+		    }
+		    
+		    short myPort = 0;
+		    String idStr = myPortObj.getPortId();
+		    String[] splitter = idStr.split(IDBOperation.PORT_ID_DELIM);
+		    if (splitter.length != 2) {
+	            log.error("Invalid port_id : {}", idStr);
+	            continue;
+		    }
+		    String myDpid = splitter[0];
+		    myPort = Short.parseShort(splitter[1]);
+		    long myId = HexString.toLong(myDpid);
+		    Node me = nodesMap.get(myId);
+		    
+		    if (me == null) {
+		        // cannot proceed ports and switches are out of sync
+		        //TODO: Restart the whole read
+		        continue;
+		    }
+		    
+		    if (me.getPort((int)myPort) == null) {
+	            me.addPort((int)myPort);
+		    } else if (me.getLink((int)myPort) != null) {
+		        // Link already added..probably by neighbor
+		        continue;
+		    }
+		
+		    //
+		    // The neighbor Port info
+		    //
+		    for (Vertex neighborPortVertex : myPortVertex.getVertices(Direction.OUT, "link")) {
+		        // Ignore inactive ports
+		        if (! neighborPortVertex.getProperty("state").toString().equals("ACTIVE")) {
+	                continue;
+		        }
+		        int neighborPort = 0;
+		        idStr = neighborPortVertex.getProperty("port_id").toString();
+		        splitter = idStr.split(IDBOperation.PORT_ID_DELIM);
+		        if (splitter.length != 2) {
+	                log.error("Invalid port_id : {}", idStr);
+	                continue;
+		        }
+		        String neighborDpid = splitter[0];
+		        neighborPort = Short.parseShort(splitter[1]);
+		        long neighborId = HexString.toLong(neighborDpid);                                
+		        Node neighbor = nodesMap.get(neighborId);
+		        if (neighbor == null) {
+	                continue;
+		        }
+		        if (neighbor.getPort(neighborPort) == null) {
+		        	neighbor.addPort(neighborPort);
+		        }
+		        me.addLink(myPort, neighbor, neighborPort);
+		    }
+		}
+		dbHandler.commit();
     }
-
+    
     // Only for debug use
     @Override
     public String toString() {
