Commit f075afdf authored by Tiago Peixoto's avatar Tiago Peixoto
Browse files

Small cleanups in graph_io.cc

parent 6c87b9b6
## Process this file with automake to produce Makefile.in
SUBDIRS = generation stats clustering community util topology centrality correlations flow layout search
SUBDIRS = centrality clustering community correlations flow generation layout search stats topology util
AM_CPPFLAGS =\
-I$(srcdir)/.. \
......@@ -18,8 +18,16 @@ libgraph_tool_coredir = $(pythondir)/graph_tool
libgraph_tool_core_LTLIBRARIES = libgraph_tool_core.la
libgraph_tool_core_la_SOURCES = \
graph_bind.cc \
../boost-workaround/boost/graph/betweenness_centrality.hpp \
../boost-workaround/boost/graph/detail/read_graphviz_new.hpp \
../boost-workaround/boost/graph/graphml.hpp \
../boost-workaround/boost/graph/graphviz.hpp \
../boost-workaround/boost/graph/isomorphism.hpp \
../boost-workaround/boost/graph/kamada_kawai_spring_layout.hpp \
../boost-workaround/boost/graph/overloading.hpp \
../boost-workaround/boost/graph/push_relabel_max_flow.hpp \
graph.cc \
graph_bind.cc \
graph_copy.cc \
graph_filtering.cc \
graph_io.cc \
......@@ -30,35 +38,28 @@ libgraph_tool_core_la_SOURCES = \
graph_python_interface.cc \
graph_python_interface_export.cc \
graph_selectors.cc \
graphml.cpp\
read_graphviz_new.cpp\
../boost-workaround/boost/graph/graphml.hpp\
../boost-workaround/boost/graph/graphviz.hpp\
../boost-workaround/boost/graph/detail/read_graphviz_new.hpp\
../boost-workaround/boost/graph/betweenness_centrality.hpp\
../boost-workaround/boost/graph/overloading.hpp\
../boost-workaround/boost/graph/isomorphism.hpp\
../boost-workaround/boost/graph/kamada_kawai_spring_layout.hpp\
../boost-workaround/boost/graph/push_relabel_max_flow.hpp
graphml.cpp \
read_graphviz_new.cpp
libgraph_tool_core_la_includedir = $(pythondir)/graph_tool/include
libgraph_tool_core_la_include_HEADERS = \
../../config.h \
fast_vector_property_map.hh \
graph.hh \
graph_adaptor.hh \
graph_wrap.hh \
graph_filtering.hh \
graph_exceptions.hh \
graph.hh \
graph_filtering.hh \
graph_properties.hh \
graph_properties_group.hh \
graph_python_interface.hh \
graph_selectors.hh \
graph_util.hh \
graph_wrap.hh \
histogram.hh \
mpl_nested_loop.hh \
shared_map.hh \
fast_vector_property_map.hh \
numpy_bind.hh \
../../config.h
str_repr.hh \
shared_map.hh
libgraph_tool_core_la_LIBADD = $(MOD_LIBADD)
libgraph_tool_core_la_LDFLAGS = $(MOD_LDFLAGS)
......
......@@ -36,6 +36,7 @@
#include <boost/xpressive/xpressive.hpp>
#include "graph_python_interface.hh"
#include "str_repr.hh"
using namespace std;
using namespace boost;
......@@ -48,135 +49,6 @@ using namespace graph_tool;
#define DP_SMART_PTR std::auto_ptr
#endif
//
// Data type string representation
// ===============================
//
// String representation of individual data types. We have to take care
// specifically that no information is lost with floating point I/O.
namespace boost
{
template <>
string lexical_cast<string,uint8_t>(const uint8_t& val)
{
// "chars" should be printed as numbers, since they can be non-printable
return lexical_cast<std::string>(int(val));
}
template <>
uint8_t lexical_cast<uint8_t,string>(const string& val)
{
// "chars" should be printed as numbers, since they can be non-printable
return uint8_t(lexical_cast<int>(val));
}
// double and long double should be printed in hexadecimal format to preserve
// internal representation
template <>
string lexical_cast<string,double>(const double& val)
{
char* str = 0;
int retval = asprintf(&str, "%la", val);
if (retval == -1)
throw bad_lexical_cast();
std::string ret = str;
free(str);
return ret;
}
template <>
double lexical_cast<double,string>(const string& val)
{
double ret;
int nc = sscanf(val.c_str(), "%la", &ret);
if (nc != 1)
throw bad_lexical_cast();
return ret;
}
template <>
string lexical_cast<string,long double>(const long double& val)
{
char* str = 0;
int retval = asprintf(&str, "%La", val);
if (retval == -1)
throw bad_lexical_cast();
std::string ret = str;
free(str);
return ret;
}
template <>
long double lexical_cast<long double,string>(const string& val)
{
long double ret;
int nc = sscanf(val.c_str(), "%La", &ret);
if (nc != 1)
throw bad_lexical_cast();
return ret;
}
}
// std::vector<> stream i/o
namespace std
{
// string vectors need special attention, since separators must be properly
// escaped.
template <>
ostream& operator<<(ostream& out, const vector<string>& vec)
{
for (size_t i = 0; i < vec.size(); ++i)
{
string s = vec[i];
// escape separators
boost::replace_all(s, "\\", "\\\\");
boost::replace_all(s, ", ", ",\\ ");
out << s;
if (i < vec.size() - 1)
out << ", ";
}
return out;
}
template <>
istream& operator>>(istream& in, vector<string>& vec)
{
using namespace boost;
using namespace boost::algorithm;
using namespace boost::xpressive;
vec.clear();
string data;
while (in.good())
{
string line;
getline(in, line);
data += line;
}
if (data == "")
return in; // empty string is OK
sregex re = sregex::compile(", ");
sregex_token_iterator iter(data.begin(), data.end(), re, -1), end;
for (; iter != end; ++iter)
{
vec.push_back(*iter);
// un-escape separators
boost::replace_all(vec.back(), ",\\ ", ", ");
boost::replace_all(vec.back(), "\\\\", "\\");
}
return in;
}
} // std namespace
//
// Persistent IO of python::object types. All the magic is done in python,
// through the object_pickler and object_unplickler below
......
// graph-tool -- a general graph modification and manipulation thingy
//
// Copyright (C) 2007-2011 Tiago de Paula Peixoto <tiago@skewed.de>
//
// This program is free software; you can redistribute it and/or
// modify it under the terms of the GNU General Public License
// as published by the Free Software Foundation; either version 3
// of the License, or (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
#ifndef STR_REPR_HH
#define STR_REPR_HH
#include <iostream>
#include <boost/lexical_cast.hpp>
#include <boost/algorithm/string.hpp>
//
// Data type string representation
// ===============================
//
// String representation of individual data types. Among other things, we have
// to take care specifically that no information is lost with floating point
// I/O.
//
namespace boost
{
//
// "chars" should be printed as numbers, since they can be non-printable
//
template <>
string lexical_cast<string,uint8_t>(const uint8_t& val)
{
return lexical_cast<std::string>(int(val));
}
template <>
uint8_t lexical_cast<uint8_t,string>(const string& val)
{
return uint8_t(lexical_cast<int>(val));
}
// float, double and long double should be printed in hexadecimal format to
// preserve internal representation
template <>
string lexical_cast<string,float>(const float& val)
{
char* str = 0;
int retval = asprintf(&str, "%a", val);
if (retval == -1)
throw bad_lexical_cast();
std::string ret = str;
free(str);
return ret;
}
template <>
float lexical_cast<float,string>(const string& val)
{
float ret;
int nc = sscanf(val.c_str(), "%a", &ret);
if (nc != 1)
throw bad_lexical_cast();
return ret;
}
template <>
string lexical_cast<string,double>(const double& val)
{
char* str = 0;
int retval = asprintf(&str, "%la", val);
if (retval == -1)
throw bad_lexical_cast();
std::string ret = str;
free(str);
return ret;
}
template <>
double lexical_cast<double,string>(const string& val)
{
double ret;
int nc = sscanf(val.c_str(), "%la", &ret);
if (nc != 1)
throw bad_lexical_cast();
return ret;
}
template <>
string lexical_cast<string,long double>(const long double& val)
{
char* str = 0;
int retval = asprintf(&str, "%La", val);
if (retval == -1)
throw bad_lexical_cast();
std::string ret = str;
free(str);
return ret;
}
template <>
long double lexical_cast<long double,string>(const string& val)
{
long double ret;
int nc = sscanf(val.c_str(), "%La", &ret);
if (nc != 1)
throw bad_lexical_cast();
return ret;
}
} // namespace boost
//
// stream i/o of std::vector<>
//
namespace std
{
// string vectors need special attention, since separators must be properly
// escaped.
template <>
ostream& operator<<(ostream& out, const vector<string>& vec)
{
for (size_t i = 0; i < vec.size(); ++i)
{
string s = vec[i];
// escape separators
boost::replace_all(s, "\\", "\\\\");
boost::replace_all(s, ", ", ",\\ ");
out << s;
if (i < vec.size() - 1)
out << ", ";
}
return out;
}
template <>
istream& operator>>(istream& in, vector<string>& vec)
{
using namespace boost;
using namespace boost::algorithm;
using namespace boost::xpressive;
vec.clear();
string data;
while (in.good())
{
string line;
getline(in, line);
data += line;
}
if (data == "")
return in; // empty string is OK
sregex re = sregex::compile(", ");
sregex_token_iterator iter(data.begin(), data.end(), re, -1), end;
for (; iter != end; ++iter)
{
vec.push_back(*iter);
// un-escape separators
boost::replace_all(vec.back(), ",\\ ", ", ");
boost::replace_all(vec.back(), "\\\\", "\\");
}
return in;
}
} // std namespace
#endif // STR_REPR_HH
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment