objectstream.cpp
来自「算断裂的」· C++ 代码 · 共 944 行 · 第 1/2 页
CPP
944 行
os << "vertex " << patch.control_point(0) << " "; } else if (fspec.fdim() == 1) { os << "bezier_curve " << patch.degree1() << " "; for (int j = 0; j < patch.degree1() + 1; ++j) { os << patch.control_point(j) << " "; } } else if (fspec.fdim() == 2) { if (patch.ptype() == BEZIER_QUAD) { os << "bezier_quad " << patch.degree1() << " " << patch.degree2() << " "; int k = 0; for (int j = 0; j < patch.degree2() + 1; ++j) { for (int i = 0; i < patch.degree1() + 1; ++i) { os << patch.control_point(k++) << " "; } } } else { os << "bezier_triangle " << patch.degree1() << " "; int ncp = (patch.degree1() + 1) * (patch.degree1() + 2) / 2; for (int j = 0; j < ncp; ++j) { os << patch.control_point(j) << " "; } } } os << ")"; } os << " )\n"; } os << nobreak_begin << " ) # end topological " << facetype << "\n" << nobreak_end; } return ostr;}// ------------------------------------------------------------------// operator<< for meshes.// This routine outputs a mesh to a stream in Ascii form.QMG::ostream& operator<<(QMG::ostream& os, const QMG::SimpComplex& sc) { int di = sc.embedded_dim(); int gdim = sc.gdim(); os << sc.io_header_code() << " " << gdim << " " << di << "\n("; int npv = sc.num_prop_val(); for (int pvi = 0; pvi < npv; ++pvi) { os << sc.prop(pvi) << " " << sc.val(pvi); } os << ")\n( # begin list of mesh nodes\n"; for (SimpComplex::VertexOrdinalIndex vnumo = 0; vnumo < sc.num_nodes(); ++vnumo) { os << sc.ordinal_to_global(vnumo) << " "; for (int ii = 0; ii < di; ++ii) { os << std::setprecision(17) << sc.real_coord_o(vnumo, ii) << " "; } os << '\n'; } os << ") # end list of mesh nodes\n"; for (int fdim = 0; fdim <= gdim; ++fdim) { os << "\n( # begin mesh info for topological entities of dimension " << fdim << '\n'; for (Brep::FaceIndex faceind = 0; faceind < sc.brep_levelsize(fdim); ++faceind) { Brep::Face_Spec fspec(fdim, faceind); os << "("; if (fdim > 0 && fdim < di) os << " # mesh vertices lying on top. entity " << fspec << '\n'; int nnf = sc.num_node_on_face(fspec); for (int seqno1 = 0; seqno1 < nnf; ++seqno1) { os << sc.node_on_face(fspec, seqno1) << " "; if (fdim > 0) { os << sc.patchind_on_face(fspec, seqno1) << " "; for (int l = 0; l < fdim; ++l) { os << std::setprecision(17) << sc.param_coord_on_face(fspec, seqno1, l) << " "; } os << '\n'; } } os << ") ("; if (fdim > 0) { os << " # mesh entities lying on top. entity " << fspec << '\n'; int nmf = sc.num_meshface_on_face(fspec); for (int seqno2 = 0; seqno2 < nmf; ++seqno2) { for (int l = 0; l < fdim + 1; ++l) { os << sc.node_of_meshface_on_face(fspec, seqno2, l) << " "; } os << '\n'; } } os << ") # " << fspec << '\n'; } os << ") # end mesh info for topological entities of dimension " << fdim << '\n'; } return os;} // ------------------------------------------------------------------// Read a brep from an istream.// Second argument is true if the header code has already been read// by another reader. Third argument indicates the number of lines of// the file already read.QMG::Brep_Under_ConstructionQMG::Brep_Under_Construction::read_from_istream(istream& istr, bool code_already_read, int& line_count) { // current_op keeps track of the current operation of the parser; // used for issuing intelligent error messages. Error_Message errinfo; errinfo.set_string("Error occurred while reading header info"); Istream_skip_comments is(istr, line_count); if (!code_already_read) { string code; is.get_string(code); if (compare_nocase(code, Brep::io_header_code())) throw_error("File begins with incorrect code"); } int gdim, embedded_dim; if (!is.get_int(gdim)) throw_error("Misplaced right paren"); if (!is.get_int(embedded_dim)) throw_error("Misplaced right paren"); errinfo.set_string("Error occurred while brep's prop-val pairs"); Brep_Under_Construction newbrep(gdim, embedded_dim); Propval_inserter pvi(newbrep); is.get_left_paren(); for (;;) { string prop, val; if (!is.get_string(prop)) break; bool s2 = is.get_string(val); if (!s2) throw_error("Unmatched property (property-values must come in pairs)"); pvi.insert_propval(prop,val); } errinfo.set_string("Error occurred while reading control points"); is.get_left_paren(); Control_point_inserter cpi(newbrep); vector<Real> coord(embedded_dim, 0.0); for (;;) { bool double_read; for (int j = 0; j < embedded_dim; ++j) { double_read = is.get_double(coord[j]); if (!double_read) { if (j > 0) { string errmsg = "number of doubles in control point list"; errmsg += " must be divisible by embedded_dim"; throw_error(errmsg); } break; } } if (!double_read) break; cpi.insert_control_point(coord); } // This map is the associative map FaceName -> Fspec since // the ascii format refers to topological faces via their // symbolic names. Face_lookup_map_type facename_lookup; for (int dim = 0; dim <= gdim; ++dim) { const char* facetype = "unknown"; if (dim == 0) facetype = "vertex"; else if (dim == 1) facetype = "edge"; else if (dim == 2) facetype = "surfaces"; else if (dim == 3) facetype = "region"; { ostringstream ost1; ost1 << "Error occurred while reading " << facetype << " list"; errinfo.set_string(ost1.str()); } Top_face_inserter tfi(newbrep, dim); is.get_left_paren(); for (;;) { string facename; if (!is.get_string(facename)) break; Brep::Face_Spec fspec = tfi.insert_top_face(facename); facename_lookup.insert(facename, fspec); { ostringstream ost1; ost1 << "Error occurred while reading property-value list of topological " << facetype << " \"" << facename << "\""; errinfo.set_string(ost1.str()); } // Insert property value pairs. Top_face_propval_inserter tpvi(newbrep, fspec); is.get_left_paren(); for (;;) { string prop, val; if (!is.get_string(prop)) break; bool s2 = is.get_string(val); if (!s2) throw_error("Unmatched property (property-values must come in pairs)"); tpvi.insert_propval(prop,val); } // Insert bounding faces. Note: bounding faces may be prefixed // by + or - to indicate orientation. { ostringstream ost1; ost1 << "Error occurred while reading boundaries of topological " << facetype << " \"" << facename << "\""; errinfo.set_string(ost1.str()); } Top_face_bound_inserter tbi(newbrep, fspec); is.get_left_paren(); for (;;) { string subfacename; if (!is.get_string(subfacename)) break; int ori = 2; if (subfacename[0] == '+') { ori = 0; subfacename = subfacename.substr(1, subfacename.length() - 1); } else if (subfacename[0] == '-') { ori = 1; subfacename = subfacename.substr(1, subfacename.length() - 1); } Brep::Face_Spec subfspec = facename_lookup.find(subfacename); tbi.insert_boundary(subfspec, ori); } // Insert internal bounding faces. { ostringstream ost1; ost1 << "Error occurred while reading internal boundaries of topological " << facetype << " \"" << facename << "\""; errinfo.set_string(ost1.str()); } Top_face_ib_inserter ibi(newbrep, fspec); is.get_left_paren(); for (;;) { string subfacename; if (!is.get_string(subfacename)) break; Brep::Face_Spec subspec = facename_lookup.find(subfacename); if (subspec.fdim() == dim - 1) { tbi.insert_boundary(subspec, 2); tbi.insert_boundary(subspec, 2); } else { ibi.insert_ib(subspec); } } // Insert patches { ostringstream ost1; ost1 << "Error occurred while reading patches of topological " << facetype << " \"" << facename << "\""; errinfo.set_string(ost1.str()); } Top_face_patch_inserter pti(newbrep, fspec); is.get_left_paren(); vector<Brep::ControlPointIndex> cp; int patchcount = 0; for (;;) { string patchstr; if (!is.get_string(patchstr)) break; ++patchcount; istringstream is2a(patchstr); Istream_skip_comments is2(is2a); is2.get_left_paren(); string patchcode; bool string_read2 = is2.get_string(patchcode); if (!string_read2) throw_error("Missing patch type name"); PatchType ptype = BEZIER_TRIANGLE; if (dim == 0) { if (compare_nocase(patchcode, "vertex") != 0) throw_error("Patch type must be 'vertex' for topological vertices"); } else if (dim == 1) { if (compare_nocase(patchcode, "bezier_curve") != 0) throw_error("Patch type must be 'bezier_curve' for topological edges"); } else if (dim == 2) { if (compare_nocase(patchcode, "bezier_quad") == 0) ptype = BEZIER_QUAD; else if (compare_nocase(patchcode, "bezier_triangle") == 0) ptype = BEZIER_TRIANGLE; else throw_error("Patch type must be either bezier_quad or bezier_triangle\n" "for topological surface"); } else { throw_error("No patches allowed here"); } int degree1, degree2; if (dim >= 1) { bool int_read = is2.get_int(degree1); if (!int_read) throw_error("Order (integer) missing"); } if (dim == 2 && ptype == BEZIER_QUAD) { bool int_read = is2.get_int(degree2); if (!int_read) throw_error("Order (integer) missing (2)"); } cp.resize(0); for (;;) { Brep::ControlPointIndex cpi; if (!is2.get_int(cpi)) break; cp.push_back(cpi); } pti.insert_patch(degree1, degree2, ptype, cp); } if (dim == 0 && patchcount != 1) { throw_error("Topological vertex must have exactly one patch"); } } } line_count = is.linecount(); return newbrep;}// ------------------------------------------------------------------// Read a mesh from an istream.// Second argument is true if the header code has already been read// by another reader. Third argument indicates the number of lines of// the file already read.QMG::SimpComplex_Under_ConstructionQMG::SimpComplex_Under_Construction::read_from_istream(istream& istr, bool code_already_read, int& line_count) { // errinfo keeps track of the current operation of the parser; // used for issuing intelligent error messages. Error_Message errinfo; errinfo.set_string("Error occurred while reading header info"); Istream_skip_comments is(istr, line_count); if (!code_already_read) { string code; is.get_string(code); if (compare_nocase(code, SimpComplex::io_header_code())) throw_error("File begins with incorrect code"); } int gdim, embedded_dim; if (!is.get_int(gdim)) throw_error("Misplaced right paren"); if (!is.get_int(embedded_dim)) throw_error("Misplaced right paren"); errinfo.set_string("Error occurred while mesh's prop-val pairs"); vector<int> levsize(gdim + 1, 0); SimpComplex_Under_Construction newsc(gdim, embedded_dim, levsize); is.get_left_paren(); for (;;) { string prop, val; if (!is.get_string(prop)) break; bool s2 = is.get_string(val); if (!s2) throw_error("Unmatched property (property-values must come in pairs)"); newsc.add_prop_val(prop,val); } errinfo.set_string("Error occurred while reading node coordinates"); is.get_left_paren(); int vnum = 0; vector<Real> realcoord(embedded_dim); for (;;) { SimpComplex::VertexGlobalIndex vnum; if (!is.get_int(vnum)) break; for (int j = 0; j < embedded_dim; ++j) { if (!is.get_double(realcoord[j])) throw_error("Missing or unbalanced number of doubles (real node coords)"); } newsc.add_vertex(realcoord,vnum); } vector<Real> paramcoord; vector<SimpComplex::VertexGlobalIndex> vlist; for (int fdim = 0; fdim <= gdim; ++fdim) { is.get_left_paren(); Brep::FaceIndex faceind = 0; paramcoord.resize(fdim); vlist.resize(fdim + 1); for (;;) { Brep::Face_Spec fspec(fdim,faceind); { ostringstream ost1; ost1 << "Error occurred while reading nodes incident on top. entity" << fspec; errinfo.set_string(ost1.str()); } if (!is.get_left_paren2()) break; newsc.add_fspec(fspec); for (;;) { SimpComplex::VertexGlobalIndex vnum; if (!is.get_int(vnum)) break; Brep::PatchIndex patchind = 0; if (fdim > 0) { if (!is.get_int(patchind)) throw_error("Missing integer (curve/patch index)"); } for (int j = 0; j < fdim; ++j) { if (!is.get_double(paramcoord[j])) throw_error("Missing double (param coord of node on top. entity)"); } newsc.add_vertex_bdryinc(vnum, fspec, patchind, paramcoord); } { ostringstream ost1; ost1 << "Error occurred while reading mesh entities lying on top. entity" << fspec; errinfo.set_string(ost1.str()); } is.get_left_paren(); for (;;) { bool done = false; for (int j = 0; j < fdim + 1; ++j) { if (!is.get_int(vlist[j])) { if (j == 0) { done = true; break; } else { throw_error("Wrong number of integers in list of mesh entities"); } } } if (done) break; newsc.add_simplex_face(vlist, fspec); } ++faceind; } } line_count = is.linecount(); return newsc;}// Reads just the header code from an istream, and determines whether// the file contains a mesh or a brep. It keeps track of the number// of lines read (for the purpose of useful error messages).QMG::Object_Type_CodeQMG::read_header_from_istream(istream& istr, int& line_count) { Error_Message errinfo; errinfo.set_string("Error occurred while reading file type"); Istream_skip_comments is(istr, line_count); string code; is.get_string(code); line_count = is.linecount(); if (compare_nocase(code, Brep::io_header_code()) == 0) return BREP; else if (compare_nocase(code, SimpComplex::io_header_code()) == 0) return SIMPCOMPLEX; else return UNKNOWN;}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?