lsgrmSegmenter.h 6.86 KB
Newer Older
1 2
#ifndef __LSRM_SEGMENTER_H
#define __LSRM_SEGMENTER_H
3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21

// Check windows
#if _WIN32 || _WIN64
#if _WIN64
#define ENVIRONMENT64
#else
#define ENVIRONMENT32
#endif
#endif

// Check GCC
#if __GNUC__
#if __x86_64__ || __ppc64__
#define ENVIRONMENT64
#else
#define ENVIRONMENT32
#endif
#endif

22
#include "macro-generator.h"
23
#include "grmSegmenter.h"
remicres's avatar
remicres committed
24 25
#include "lsgrmGraphToOtbImage.h"
namespace lsgrm
26
{
27 28 29 30 31 32 33 34 35 36 37 38
template<class TSegmenterType>
class Segmenter : public TSegmenterType
{
public:

  /* Some convenient typedefs */

  typedef typename TSegmenterType::ImageType ImageType;
  typedef typename TSegmenterType::NodeType NodeType;
  typedef typename TSegmenterType::ParamType ParamType;
  typedef grm::Graph<NodeType> GraphType;
  typedef typename GraphType::EdgeType EdgeType;
39
  typedef typename GraphType::EdgeListType EdgeListType;
40 41
  typedef typename grm::GraphOperations<TSegmenterType> GraphOperatorType;
  typedef typename GraphOperatorType::NodePointerType NodePointerType;
remicres's avatar
remicres committed
42
  typedef GraphToOtbImage<GraphType> IOType;
43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141
  typedef typename IOType::LabelImageType LabelImageType;

  ~Segmenter(){};

  /*
   * Given 1 smart node pointer (boost::shared_ptr), this
   * method writes the node specific attributes into the node stream.
   *
   * @params
   * NodePointerType n : Smart pointer of node
   *
   */
  virtual void WriteSpecificAttributes(NodePointerType node, FILE * nodeStream) = 0;

  /*
   * Given 1 smart node pointer (boost::shared_ptr), this
   * method read the node specific attributes from the node stream.
   *
   * @params
   * NodePointerType n : Smart pointer of node
   * FILE * nodeStream : Node stream
   *
   */
  virtual void ReadSpecificAttributes(NodePointerType node, FILE * nodeStream) = 0;

  /*
   * Given 1 smart node pointer (boost::shared_ptr), this
   * method writes the node into a stream.
   *
   * @params
   * NodePointerType n : Smart pointer of node
   * FILE * nodeStream : Node stream
   *
   */
  void WriteNode(NodePointerType node, FILE * nodeStream)
  {
    fwrite(&(node->m_Id), sizeof(node->m_Id), 1, nodeStream);
    fwrite(&(node->m_Perimeter), sizeof(node->m_Perimeter), 1, nodeStream);
    fwrite(&(node->m_Area), sizeof(node->m_Area), 1, nodeStream);
    fwrite(&(node->m_Bbox.m_UX), sizeof(node->m_Bbox.m_UX), 1, nodeStream);
    fwrite(&(node->m_Bbox.m_UY), sizeof(node->m_Bbox.m_UY), 1, nodeStream);
    fwrite(&(node->m_Bbox.m_W), sizeof(node->m_Bbox.m_W), 1, nodeStream);
    fwrite(&(node->m_Bbox.m_H), sizeof(node->m_Bbox.m_H), 1, nodeStream);

    this->WriteSpecificAttributes(node, nodeStream);

    std::size_t contourSize = node->m_Contour.size();
    fwrite(&(contourSize), sizeof(contourSize), 1, nodeStream);
    short moves[contourSize];
    for(unsigned int b = 0; b < contourSize; b++)
      {
      moves[b] = node->m_Contour[b];
      }
    fwrite(moves, sizeof(short), contourSize, nodeStream);
  }

  /*
   * This method reads a graph from a stream.
   *
   * @params
   * FILE * nodeStream : Node stream
   *
   */
  void ReadGraph(FILE * nodeStream, FILE * edgeStream)
  {

    std::unordered_map<long unsigned int, NodePointerType> nodeMap;

    // Read the size of the graph
    {
    std::size_t graphSize;
    fread(&graphSize, sizeof(graphSize), 1, nodeStream);
    this->m_Graph.m_Nodes.reserve(graphSize);

    // Creation of the nodes
    for(std::size_t i = 0; i < graphSize; i++)
      {
      NodePointerType node(new NodeType());

      node->m_Valid = true;
      node->m_Expired = false;
      node->m_IsMerged = true; // force to compute costs for the first iteration

      fread(&(node->m_Id), sizeof(node->m_Id), 1, nodeStream);
      fread(&(node->m_Perimeter), sizeof(node->m_Perimeter), 1, nodeStream);
      fread(&(node->m_Area), sizeof(node->m_Area), 1, nodeStream);
      fread(&(node->m_Bbox.m_UX), sizeof(node->m_Bbox.m_UX), 1, nodeStream);
      fread(&(node->m_Bbox.m_UY), sizeof(node->m_Bbox.m_UY), 1, nodeStream);
      fread(&(node->m_Bbox.m_W), sizeof(node->m_Bbox.m_W), 1, nodeStream);
      fread(&(node->m_Bbox.m_H), sizeof(node->m_Bbox.m_H), 1, nodeStream);

      this->ReadSpecificAttributes(node, nodeStream);

      {
        std::size_t contourSize;
        fread(&(contourSize), sizeof(contourSize), 1, nodeStream);
        short moves[contourSize];
        fread(&moves, sizeof(short), contourSize, nodeStream);
        for(unsigned int b = 0; b < contourSize; b++)
142
          {
143
          node->m_Contour.push_back(moves[b]);
144
          }
145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160
      }
      nodeMap[node->m_Id] = node;
      this->m_Graph.m_Nodes.push_back(node);
      }
    }

    for(auto& node: this->m_Graph.m_Nodes)
      {
      long unsigned int nodeId;
      fread(&(nodeId), sizeof(nodeId), 1, edgeStream);
      assert(nodeId == node->m_Id);

      std::size_t edgeSize;
      fread(&(edgeSize), sizeof(edgeSize), 1, edgeStream);
      node->m_Edges.reserve(edgeSize);
      for(unsigned int b = 0; b < edgeSize; b++)
161
        {
162 163 164 165 166
        long unsigned int targetId;
        unsigned int boundary;
        fread(&(targetId), sizeof(targetId), 1, edgeStream);
        fread(&(boundary), sizeof(boundary), 1, edgeStream);
        node->m_Edges.push_back(EdgeType(nodeMap[targetId], 0, boundary));
167
        }
168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185
      }

  }

  /*
   * This method writes the edge into a stream.
   *
   * @params
   * EdgePointerType edg : Smart pointer of edge
   *
   */
  void WriteEdge(typename NodeType::CRPTNeighborType edg, FILE * edgeStream)
  {
    fwrite(&(edg.GetRegion()->m_Id), sizeof(edg.GetRegion()->m_Id), 1, edgeStream);
    fwrite(&(edg.m_Boundary), sizeof(edg.m_Boundary), 1, edgeStream);
  }

  /*
186
   * Returns the memory (in bytes) occupied by the specific attributes of the node
187
   */
188
  virtual long long unsigned int GetSpecificAttributesMemory(NodePointerType &node) = 0;
189 190 191 192 193 194 195

  /*
   * Returns the memory (in bytes) occupied by the entire graph
   */
  long long unsigned int GetGraphMemory()
  {
    long long unsigned int memory = 0;
196

197 198 199
    // sizeof(graph)... even if not significant
    memory += sizeof(GraphType);

200 201
    for(auto& node : this->m_Graph.m_Nodes)
      {
202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222
      // size of the contour (boost::dynamic_bitset)
      memory += sizeof(lp::Contour);
#ifdef ENVIRONMENT64
      memory += 8 * ((node->m_Contour.size() + 63) / 64);
#endif
#ifdef ENVIRONMENT32
      memory += 8 * ((node->m_Contour.size() + 31) / 32);
#endif

      // size of specific attributes
      memory += this->GetSpecificAttributesMemory(node);

      // size of the node pointer
      memory += sizeof(NodePointerType);

      // size of the node (actually, size of the base node)
      memory += sizeof(NodeType);

      // size of the edges
      memory += node->m_Edges.capacity() * sizeof(EdgeType);
      memory += sizeof(EdgeListType);
223 224 225 226 227 228 229 230 231 232 233 234 235 236
      }

    return memory;
  }

  /* Return the label image */
  inline typename LabelImageType::Pointer GetLabeledClusteredOutput()
  {
    IOType io;
    auto labelImg = io.GetLabelImage(this->m_Graph, this->m_ImageWidth, this->m_ImageHeight);
    return labelImg;
  }

};
remicres's avatar
remicres committed
237
} // end of namespace lsgrm
238 239 240 241 242 243

#endif