message: Make NodeIter and NeighborIter more like real c++ iterators.
  Reference:
diff: @@ -770,15 +770,20 @@ inline bool IsHostMemoryPreserving(const Node* node) {
  return IsIdentity(node) || IsControlFlow(node);
  }
  +// NOTE: We declare Reference type of NodeIter and NeighborIter as Node* (see
  +// https://en.cppreference.com/w/cpp/iterator/iterator).
  +
  // Iterator for stepping through the nodes of a graph.
  -class NodeIter {
  +class NodeIter
  + : public std::iterator<std::forward_iterator_tag, Node, std::ptrdiff_t,
  + /*Pointer*/ Node*, /*Reference*/ Node*> {
  public:
  NodeIter(const Graph* graph, int id);
  - bool operator==(const NodeIter& rhs);
  - bool operator!=(const NodeIter& rhs);
  + bool operator==(const NodeIter& rhs) const;
  + bool operator!=(const NodeIter& rhs) const;
  void operator++();
  - Node* operator*();
  - Node* operator->();
  + reference operator*() const;
  + pointer operator->() const;
  private:
  // Invariant: id_ == graph_->num_node_ids() || graph_->FindId(id_) != nullptr
  @@ -787,14 +792,16 @@ class NodeIter {
  };
  // Iterator for stepping through the neighbors of a node.
  -class NeighborIter {
  +class NeighborIter
  + : public std::iterator<std::forward_iterator_tag, Node, std::ptrdiff_t,
  + /*Pointer*/ Node*, /*Reference*/ Node*> {
  public:
  NeighborIter(EdgeSet::const_iterator iter, bool incoming);
  - bool operator==(const NeighborIter& rhs);
  - bool operator!=(const NeighborIter& rhs);
  + bool operator==(const NeighborIter& rhs) const;
  + bool operator!=(const NeighborIter& rhs) const;
  void operator++();
  - Node* operator*();
  - Node* operator->();
  + reference operator*() const;
  + pointer operator->() const;
  private:
  EdgeSet::const_iterator iter_;
  @@ -806,12 +813,12 @@ class NeighborIter {
  inline NodeIter::NodeIter(const Graph* graph, int id)
  : graph_(graph), id_(id) {}
  -inline bool NodeIter::operator==(const NodeIter& rhs) {
  +inline bool NodeIter::operator==(const NodeIter& rhs) const {
  DCHECK(graph_ == rhs.graph_);
  return id_ == rhs.id_;
  }
  -inline bool NodeIter::operator!=(const NodeIter& rhs) {
  +inline bool NodeIter::operator!=(const NodeIter& rhs) const {
  return !(*this == rhs);
  }
  @@ -825,29 +832,29 @@ inline void NodeIter::operator++() {
  }
  }
  -inline Node* NodeIter::operator*() { return graph_->FindNodeId(id_); }
  +inline Node* NodeIter::operator*() const { return graph_->FindNodeId(id_); }
  -inline Node* NodeIter::operator->() { return graph_->FindNodeId(id_); }
  +inline Node* NodeIter::operator->() const { return graph_->FindNodeId(id_); }
  inline NeighborIter::NeighborIter(EdgeSet::const_iterator iter, bool incoming)
  : iter_(iter), incoming_(incoming) {}
  -inline bool NeighborIter::operator==(const NeighborIter& rhs) {
  +inline bool NeighborIter::operator==(const NeighborIter& rhs) const {
  return iter_ == rhs.iter_ && incoming_ == rhs.incoming_;
  }
  -inline bool NeighborIter::operator!=(const NeighborIter& rhs) {
  +inline bool NeighborIter::operator!=(const NeighborIter& rhs) const {
  return !(*this == rhs);
  }
  inline void NeighborIter::operator++() { ++iter_; }
  -inline Node* NeighborIter::operator*() {
  +inline Node* NeighborIter::operator*() const {
  const Edge* e = *iter_;
  return incoming_ ? e->src() : e->dst();
  }
  -inline Node* NeighborIter::operator->() {
  +inline Node* NeighborIter::operator->() const {
  const Edge* e = *iter_;
  return incoming_ ? e->src() : e->dst();
  }
  