diff --git a/include/xlnt/xlnt_config.hpp b/include/xlnt/xlnt_config.hpp index 718f71bb..ac8ddce8 100644 --- a/include/xlnt/xlnt_config.hpp +++ b/include/xlnt/xlnt_config.hpp @@ -52,7 +52,7 @@ enum class limit_style /// The style of limits to use for reading and writing XLSX files. /// See limit_style for more information. /// -const limit_style LimitStyle = limit_style::openpyxl; +const limit_style xlnt_limit_style = limit_style::openpyxl; #ifndef XLNT_API #if !defined(XLNT_STATIC) && defined(_MSC_VER) diff --git a/source/cell/cell_reference.cpp b/source/cell/cell_reference.cpp index 0cf72a2b..2982258c 100644 --- a/source/cell/cell_reference.cpp +++ b/source/cell/cell_reference.cpp @@ -33,7 +33,7 @@ namespace xlnt { std::size_t cell_reference_hash::operator()(const cell_reference &k) const { - return k.get_row() * constants::MaxColumn().index + k.get_column_index().index; + return k.get_row() * constants::max_column().index + k.get_column_index().index; } cell_reference &cell_reference::make_absolute(bool absolute_column, bool absolute_row) @@ -74,7 +74,7 @@ cell_reference::cell_reference(column_t column_index, row_t row) throw value_error(); } - if (!(row_ <= constants::MaxRow()) || !(column_ <= constants::MaxColumn())) + if (!(row_ <= constants::max_row()) || !(column_ <= constants::max_column())) { throw cell_coordinates_error(column_, row_); } diff --git a/source/cell/index_types.cpp b/source/cell/index_types.cpp index e31cf6e5..34a2c34c 100644 --- a/source/cell/index_types.cpp +++ b/source/cell/index_types.cpp @@ -63,7 +63,7 @@ std::string column_t::column_string_from_index(column_t::index_t column_index) { // these indicies corrospond to A->ZZZ and include all allowed // columns - if (column_index < constants::MinColumn() || column_index > constants::MaxColumn()) + if (column_index < constants::min_column() || column_index > constants::max_column()) { // auto msg = "Column index out of bounds: " + std::to_string(column_index); throw column_string_index_error(); diff --git a/source/detail/constants.cpp b/source/detail/constants.cpp index 9b60b88f..ef8857d2 100644 --- a/source/detail/constants.cpp +++ b/source/detail/constants.cpp @@ -28,14 +28,14 @@ namespace xlnt { -const row_t constants::MinRow() +const row_t constants::min_row() { return 1; } -const row_t constants::MaxRow() +const row_t constants::max_row() { - if(LimitStyle == limit_style::excel) + if(xlnt_limit_style == limit_style::excel) { return 1u << 20; } @@ -43,69 +43,67 @@ const row_t constants::MaxRow() return std::numeric_limits::max(); } -const column_t constants::MinColumn() +const column_t constants::min_column() { return column_t(1); } -const column_t constants::MaxColumn() +const column_t constants::max_column() { - if(LimitStyle == limit_style::excel) + switch (xlnt_limit_style) { + case limit_style::excel: return column_t(1u << 14); + + case limit_style::openpyxl: + return column_t(18'278); + + default: + return column_t(std::numeric_limits::max()); } - - if(LimitStyle == limit_style::openpyxl) - { - return column_t(18278); - } - - return column_t(std::numeric_limits::max()); } // constants -const std::string constants::PackageProps() { return "docProps"; } -const std::string constants::PackageXl() { return "xl"; } -const std::string constants::PackageRels() { return "_rels"; } -const std::string constants::PackageTheme() { return PackageXl() + "/" + "theme"; } -const std::string constants::PackageWorksheets() { return PackageXl() + "/" + "worksheets"; } -const std::string constants::PackageDrawings() { return PackageXl() + "/" + "drawings"; } -const std::string constants::PackageCharts() { return PackageXl() + "/" + "charts"; } +const std::string constants::package_properties() { return "docProps"; } +const std::string constants::package_xl() { return "xl"; } +const std::string constants::package_root_rels() { return "_rels"; } +const std::string constants::package_theme() { return package_xl() + "/" + "theme"; } +const std::string constants::package_worksheets() { return package_xl() + "/" + "worksheets"; } -const std::string constants::ArcContentTypes() { return "[Content_Types].xml"; } -const std::string constants::ArcRootRels() { return PackageRels() + "/.rels"; } -const std::string constants::ArcWorkbookRels() { return PackageXl() + "/" + PackageRels() + "/workbook.xml.rels"; } -const std::string constants::ArcCore() { return PackageProps() + "/core.xml"; } -const std::string constants::ArcApp() { return PackageProps() + "/app.xml"; } -const std::string constants::ArcWorkbook() { return PackageXl() + "/workbook.xml"; } -const std::string constants::ArcStyles() { return PackageXl() + "/styles.xml"; } -const std::string constants::ArcTheme() { return PackageTheme() + "/theme1.xml"; } -const std::string constants::ArcSharedString() { return PackageXl() + "/sharedStrings.xml"; } +const std::string constants::part_content_types() { return "[Content_Types].xml"; } +const std::string constants::part_root_relationships() { return package_root_rels() + "/.rels"; } +const std::string constants::part_core() { return package_properties() + "/core.xml"; } +const std::string constants::part_app() { return package_properties() + "/app.xml"; } +const std::string constants::part_workbook() { return package_xl() + "/workbook.xml"; } +const std::string constants::part_styles() { return package_xl() + "/styles.xml"; } +const std::string constants::part_theme() { return package_theme() + "/theme1.xml"; } +const std::string constants::part_shared_strings() { return package_xl() + "/sharedStrings.xml"; } -const std::unordered_map constants::Namespaces() +const std::unordered_map &constants::get_namespaces() { - const std::unordered_map namespaces = - { - { "spreadsheetml", "http://schemas.openxmlformats.org/spreadsheetml/2006/main" }, - { "content-types", "http://schemas.openxmlformats.org/package/2006/content-types" }, - { "relationships", "http://schemas.openxmlformats.org/package/2006/relationships" }, - { "drawingml", "http://schemas.openxmlformats.org/drawingml/2006/main" }, - { "r", "http://schemas.openxmlformats.org/officeDocument/2006/relationships" }, - { "cp", "http://schemas.openxmlformats.org/package/2006/metadata/core-properties" }, - { "dc", "http://purl.org/dc/elements/1.1/" }, - { "dcterms", "http://purl.org/dc/terms/" }, - { "dcmitype", "http://purl.org/dc/dcmitype/" }, - { "xsi", "http://www.w3.org/2001/XMLSchema-instance" }, - { "vt", "http://schemas.openxmlformats.org/officeDocument/2006/docPropsVTypes" }, - { "xml", "http://www.w3.org/XML/1998/namespace" } - }; - - return namespaces; + const std::unordered_map *namespaces = + new std::unordered_map + { + { "spreadsheetml", "http://schemas.openxmlformats.org/spreadsheetml/2006/main" }, + { "content-types", "http://schemas.openxmlformats.org/package/2006/content-types" }, + { "relationships", "http://schemas.openxmlformats.org/package/2006/relationships" }, + { "drawingml", "http://schemas.openxmlformats.org/drawingml/2006/main" }, + { "r", "http://schemas.openxmlformats.org/officeDocument/2006/relationships" }, + { "cp", "http://schemas.openxmlformats.org/package/2006/metadata/core-properties" }, + { "dc", "http://purl.org/dc/elements/1.1/" }, + { "dcterms", "http://purl.org/dc/terms/" }, + { "dcmitype", "http://purl.org/dc/dcmitype/" }, + { "xsi", "http://www.w3.org/2001/XMLSchema-instance" }, + { "vt", "http://schemas.openxmlformats.org/officeDocument/2006/docPropsVTypes" }, + { "xml", "http://www.w3.org/XML/1998/namespace" } + }; + + return *namespaces; } -const std::string constants::Namespace(const std::string &id) +const std::string constants::get_namespace(const std::string &id) { - return Namespaces().find(id)->second; + return get_namespaces().find(id)->second; } } diff --git a/source/detail/constants.hpp b/source/detail/constants.hpp index e31b814d..432752c9 100644 --- a/source/detail/constants.hpp +++ b/source/detail/constants.hpp @@ -31,33 +31,100 @@ namespace xlnt { struct constants { - static const row_t MinRow(); - static const row_t MaxRow(); - static const column_t MinColumn(); - static const column_t MaxColumn(); + /// + /// Returns the lowest allowable row index in a worksheet. + /// + static const row_t min_row(); - // constants - static const std::string PackageProps(); - static const std::string PackageXl(); - static const std::string PackageRels(); - static const std::string PackageTheme(); - static const std::string PackageWorksheets(); - static const std::string PackageDrawings(); - static const std::string PackageCharts(); + /// + /// Returns the largest allowable row index in a worksheet. + /// + static const row_t max_row(); - static const std::string ArcContentTypes(); - static const std::string ArcRootRels(); - static const std::string ArcWorkbookRels(); - static const std::string ArcCore(); - static const std::string ArcApp(); - static const std::string ArcWorkbook(); - static const std::string ArcStyles(); - static const std::string ArcTheme(); - static const std::string ArcSharedString(); + /// + /// Returns the lowest allowable column index in a worksheet. + /// + static const column_t min_column(); - static const std::unordered_map Namespaces(); - - static const std::string Namespace(const std::string &id); + /// + /// Returns the largest allowable column index in a worksheet. + /// + static const column_t max_column(); + + /// + /// Returns the URI of the directory containing package properties. + /// + static const std::string package_properties(); + + /// + /// Returns the URI of the directory containing SpreatsheetML package parts. + /// + static const std::string package_xl(); + + /// + /// Returns the URI of the directory containing root relationships package part. + /// + static const std::string package_root_rels(); + + /// + /// Returns the URI of the directory containing package themes. + /// + static const std::string package_theme(); + + /// + /// Returns the URI of the directory containing package worksheets. + /// + static const std::string package_worksheets(); + + /// + /// Returns the URI of the content types package part. + /// + static const std::string part_content_types(); + + /// + /// Returns the URI of the core properties package part. + /// + static const std::string part_core(); + + /// + /// Returns the URI of the app properties package part. + /// + static const std::string part_app(); + + /// + /// Returns the URI of the workbook package part. + /// + static const std::string part_workbook(); + + /// + /// Returns the URI of the root relationships package part. + /// + static const std::string part_root_relationships(); + + /// + /// Returns the URI of the styles package part. + /// + static const std::string part_styles(); + + /// + /// Returns the URI of the theme package part. + /// + static const std::string part_theme(); + + /// + /// Returns the URI of the shared strings package part. + /// + static const std::string part_shared_strings(); + + /// + /// Returns an unordered_map mapping namespace names to namespaces. + /// + static const std::unordered_map &get_namespaces(); + + /// + /// Returns the namespace URI from a namespace name. + /// + static const std::string get_namespace(const std::string &id); }; } // namespace xlnt diff --git a/source/detail/excel_serializer.cpp b/source/detail/excel_serializer.cpp index 0410f900..ce11d44c 100644 --- a/source/detail/excel_serializer.cpp +++ b/source/detail/excel_serializer.cpp @@ -71,14 +71,14 @@ bool load_workbook(xlnt::zip_file &archive, bool guess_types, bool data_only, xl wb.set_guess_types(guess_types); wb.set_data_only(data_only); - if(!archive.has_file(xlnt::constants::ArcContentTypes())) + if(!archive.has_file(xlnt::constants::part_content_types())) { throw xlnt::invalid_file_error("missing [Content Types].xml"); } xlnt::manifest_serializer ms(wb.get_manifest()); pugi::xml_document manifest_xml; - manifest_xml.load(archive.read(xlnt::constants::ArcContentTypes()).c_str()); + manifest_xml.load(archive.read(xlnt::constants::part_content_types()).c_str()); ms.read_manifest(manifest_xml); if (ms.determine_document_type() != "excel") @@ -88,19 +88,19 @@ bool load_workbook(xlnt::zip_file &archive, bool guess_types, bool data_only, xl wb.clear(); - if(archive.has_file(xlnt::constants::ArcCore())) + if(archive.has_file(xlnt::constants::part_core())) { xlnt::workbook_serializer workbook_serializer_(wb); pugi::xml_document core_properties_xml; - core_properties_xml.load(archive.read(xlnt::constants::ArcCore()).c_str()); + core_properties_xml.load(archive.read(xlnt::constants::part_core()).c_str()); workbook_serializer_.read_properties_core(core_properties_xml); } - if(archive.has_file(xlnt::constants::ArcApp())) + if(archive.has_file(xlnt::constants::part_app())) { xlnt::workbook_serializer workbook_serializer_(wb); pugi::xml_document app_properties_xml; - app_properties_xml.load(archive.read(xlnt::constants::ArcApp()).c_str()); + app_properties_xml.load(archive.read(xlnt::constants::part_app()).c_str()); workbook_serializer_.read_properties_app(app_properties_xml); } @@ -112,7 +112,7 @@ bool load_workbook(xlnt::zip_file &archive, bool guess_types, bool data_only, xl wb.create_root_relationship(relationship.get_id(), relationship.get_target_uri(), relationship.get_type()); } - auto workbook_relationships = relationship_serializer_.read_relationships(xlnt::constants::ArcWorkbook()); + auto workbook_relationships = relationship_serializer_.read_relationships(xlnt::constants::part_workbook()); for (const auto &relationship : workbook_relationships) { @@ -120,7 +120,7 @@ bool load_workbook(xlnt::zip_file &archive, bool guess_types, bool data_only, xl } pugi::xml_document xml; - xml.load(archive.read(xlnt::constants::ArcWorkbook()).c_str()); + xml.load(archive.read(xlnt::constants::part_workbook()).c_str()); auto root_node = xml.child("workbook"); @@ -130,11 +130,11 @@ bool load_workbook(xlnt::zip_file &archive, bool guess_types, bool data_only, xl ? xlnt::calendar::mac_1904 : xlnt::calendar::windows_1900; - if(archive.has_file(xlnt::constants::ArcSharedString())) + if(archive.has_file(xlnt::constants::part_shared_strings())) { std::vector shared_strings; pugi::xml_document shared_strings_xml; - shared_strings_xml.load(archive.read(xlnt::constants::ArcSharedString()).c_str()); + shared_strings_xml.load(archive.read(xlnt::constants::part_shared_strings()).c_str()); xlnt::shared_strings_serializer::read_shared_strings(shared_strings_xml, shared_strings); for (auto &shared_string : shared_strings) @@ -145,7 +145,7 @@ bool load_workbook(xlnt::zip_file &archive, bool guess_types, bool data_only, xl xlnt::style_serializer style_serializer(stylesheet); pugi::xml_document style_xml; - style_xml.load(archive.read(xlnt::constants::ArcStyles()).c_str()); + style_xml.load(archive.read(xlnt::constants::part_styles()).c_str()); style_serializer.read_stylesheet(style_xml); auto sheets_node = root_node.child("sheets"); @@ -243,7 +243,7 @@ void excel_serializer::write_data(bool /*as_template*/) { relationship_serializer relationship_serializer_(archive_); relationship_serializer_.write_relationships(workbook_.get_root_relationships(), ""); - relationship_serializer_.write_relationships(workbook_.get_relationships(), constants::ArcWorkbook()); + relationship_serializer_.write_relationships(workbook_.get_relationships(), constants::part_workbook()); pugi::xml_document properties_app_xml; workbook_serializer workbook_serializer_(workbook_); @@ -252,7 +252,7 @@ void excel_serializer::write_data(bool /*as_template*/) { std::ostringstream ss; properties_app_xml.save(ss); - archive_.writestr(constants::ArcApp(), ss.str()); + archive_.writestr(constants::part_app(), ss.str()); } pugi::xml_document properties_core_xml; @@ -261,7 +261,7 @@ void excel_serializer::write_data(bool /*as_template*/) { std::ostringstream ss; properties_core_xml.save(ss); - archive_.writestr(constants::ArcCore(), ss.str()); + archive_.writestr(constants::part_core(), ss.str()); } pugi::xml_document theme_xml; @@ -271,7 +271,7 @@ void excel_serializer::write_data(bool /*as_template*/) { std::ostringstream ss; theme_xml.save(ss); - archive_.writestr(constants::ArcTheme(), ss.str()); + archive_.writestr(constants::part_theme(), ss.str()); } if (!workbook_.get_shared_strings().empty()) @@ -282,7 +282,7 @@ void excel_serializer::write_data(bool /*as_template*/) std::ostringstream ss; shared_strings_xml.save(ss); - archive_.writestr(constants::ArcSharedString(), ss.str()); + archive_.writestr(constants::part_shared_strings(), ss.str()); } pugi::xml_document workbook_xml; @@ -291,7 +291,7 @@ void excel_serializer::write_data(bool /*as_template*/) { std::ostringstream ss; workbook_xml.save(ss); - archive_.writestr(constants::ArcWorkbook(), ss.str()); + archive_.writestr(constants::part_workbook(), ss.str()); } style_serializer style_serializer(workbook_.d_->stylesheet_); @@ -301,7 +301,7 @@ void excel_serializer::write_data(bool /*as_template*/) { std::ostringstream ss; style_xml.save(ss); - archive_.writestr(constants::ArcStyles(), ss.str()); + archive_.writestr(constants::part_styles(), ss.str()); } manifest_serializer manifest_serializer_(workbook_.get_manifest()); @@ -311,7 +311,7 @@ void excel_serializer::write_data(bool /*as_template*/) { std::ostringstream ss; manifest_xml.save(ss); - archive_.writestr(constants::ArcContentTypes(), ss.str()); + archive_.writestr(constants::part_content_types(), ss.str()); } write_worksheets(); diff --git a/source/detail/manifest_serializer.cpp b/source/detail/manifest_serializer.cpp index e3155461..769f9d30 100644 --- a/source/detail/manifest_serializer.cpp +++ b/source/detail/manifest_serializer.cpp @@ -54,7 +54,7 @@ void manifest_serializer::read_manifest(const pugi::xml_document &xml) void manifest_serializer::write_manifest(pugi::xml_document &xml) const { auto root_node = xml.append_child("Types"); - root_node.append_attribute("xmlns").set_value(constants::Namespace("content-types").c_str()); + root_node.append_attribute("xmlns").set_value(constants::get_namespace("content-types").c_str()); for (const auto default_type : manifest_.get_default_types()) { @@ -73,12 +73,12 @@ void manifest_serializer::write_manifest(pugi::xml_document &xml) const std::string manifest_serializer::determine_document_type() const { - if (!manifest_.has_override_type(constants::ArcWorkbook())) + if (!manifest_.has_override_type(constants::part_workbook())) { return "unsupported"; } - std::string type = manifest_.get_override_type(constants::ArcWorkbook()); + std::string type = manifest_.get_override_type(constants::part_workbook()); if (type == "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet.main+xml") { diff --git a/source/detail/relationship_serializer.cpp b/source/detail/relationship_serializer.cpp index a2dc0a2c..eb2bb94b 100644 --- a/source/detail/relationship_serializer.cpp +++ b/source/detail/relationship_serializer.cpp @@ -36,16 +36,16 @@ std::string make_rels_name(const std::string &target) { const char sep = '/'; - if (target.empty() || target.back() == sep) + if (target.empty()) { - return target + "_rels/.rels"; + return xlnt::constants::part_root_relationships(); } auto sep_pos = target.find_last_of(sep); - auto first_part = target.substr(0, sep_pos + 1); - auto last_part = target.substr(sep_pos + 1); + auto path = target.substr(0, sep_pos + 1); + auto filename = target.substr(sep_pos + 1); - return first_part + "_rels/" + last_part + ".rels"; + return path + "_rels/" + filename + ".rels"; } } @@ -83,7 +83,7 @@ bool relationship_serializer::write_relationships(const std::vector #include +#include +#include +#include +#include +#include +#include #include #include #include @@ -50,12 +56,6 @@ #include #include -#include -#include -#include -#include -#include - namespace xlnt { namespace detail { @@ -79,11 +79,11 @@ workbook::workbook() : d_(new detail::workbook_impl()) d_->manifest_.add_default_type("rels", "application/vnd.openxmlformats-package.relationships+xml"); d_->manifest_.add_default_type("xml", "application/xml"); - d_->manifest_.add_override_type("/xl/workbook.xml", "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet.main+xml"); - d_->manifest_.add_override_type("/xl/theme/theme1.xml", "application/vnd.openxmlformats-officedocument.theme+xml"); - d_->manifest_.add_override_type("/xl/styles.xml", "application/vnd.openxmlformats-officedocument.spreadsheetml.styles+xml"); - d_->manifest_.add_override_type("/docProps/core.xml", "application/vnd.openxmlformats-package.core-properties+xml"); - d_->manifest_.add_override_type("/docProps/app.xml", "application/vnd.openxmlformats-officedocument.extended-properties+xml"); + d_->manifest_.add_override_type("/" + constants::part_workbook(), "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet.main+xml"); + d_->manifest_.add_override_type("/" + constants::part_theme(), "application/vnd.openxmlformats-officedocument.theme+xml"); + d_->manifest_.add_override_type("/" + constants::part_styles(), "application/vnd.openxmlformats-officedocument.spreadsheetml.styles+xml"); + d_->manifest_.add_override_type("/" + constants::part_core(), "application/vnd.openxmlformats-package.core-properties+xml"); + d_->manifest_.add_override_type("/" + constants::part_app(), "application/vnd.openxmlformats-officedocument.extended-properties+xml"); add_format(format()); create_style("Normal"); @@ -692,10 +692,11 @@ const std::vector &workbook::get_root_relationships() const if (d_->root_relationships_.empty()) { d_->root_relationships_.push_back( - relationship(relationship::type::core_properties, "rId1", "docProps/core.xml")); + relationship(relationship::type::core_properties, "rId1", constants::part_core())); d_->root_relationships_.push_back( - relationship(relationship::type::extended_properties, "rId2", "docProps/app.xml")); - d_->root_relationships_.push_back(relationship(relationship::type::office_document, "rId3", "xl/workbook.xml")); + relationship(relationship::type::extended_properties, "rId2", constants::part_app())); + d_->root_relationships_.push_back( + relationship(relationship::type::office_document, "rId3", constants::part_workbook())); } return d_->root_relationships_; @@ -716,9 +717,9 @@ void workbook::add_shared_string(const text &shared, bool allow_duplicates) if (d_->shared_strings_.empty()) { create_relationship(next_relationship_id(), "sharedStrings.xml", relationship::type::shared_strings); - d_->manifest_.add_override_type("/xl/sharedStrings.xml", "application/vnd.openxmlformats-officedocument.spreadsheetml.sharedStrings+xml"); + d_->manifest_.add_override_type("/" + constants::part_shared_strings(), "application/vnd.openxmlformats-officedocument.spreadsheetml.sharedStrings+xml"); } - + if (!allow_duplicates) { //TODO: inefficient, use a set or something? diff --git a/source/worksheet/tests/test_worksheet.hpp b/source/worksheet/tests/test_worksheet.hpp index 44128e73..cb47a2eb 100644 --- a/source/worksheet/tests/test_worksheet.hpp +++ b/source/worksheet/tests/test_worksheet.hpp @@ -1167,6 +1167,12 @@ public: } } } + + auto const_range = ws_const.get_range("B3:C7"); + auto const_range_iter = const_range.begin(); + const_range_iter++; + const_range_iter--; + TS_ASSERT_EQUALS(const_range_iter, const_range.begin()); } void test_range_reference() diff --git a/source/worksheet/worksheet.cpp b/source/worksheet/worksheet.cpp index f0129a68..8f3a5fd9 100644 --- a/source/worksheet/worksheet.cpp +++ b/source/worksheet/worksheet.cpp @@ -337,10 +337,10 @@ column_t worksheet::get_lowest_column() const { if (d_->cell_map_.empty()) { - return constants::MinColumn(); + return constants::min_column(); } - column_t lowest = constants::MaxColumn(); + column_t lowest = constants::max_column(); for (auto &row : d_->cell_map_) { @@ -357,10 +357,10 @@ row_t worksheet::get_lowest_row() const { if (d_->cell_map_.empty()) { - return constants::MinRow(); + return constants::min_row(); } - row_t lowest = constants::MaxRow(); + row_t lowest = constants::max_row(); for (auto &row : d_->cell_map_) { @@ -372,7 +372,7 @@ row_t worksheet::get_lowest_row() const row_t worksheet::get_highest_row() const { - row_t highest = constants::MinRow(); + row_t highest = constants::min_row(); for (auto &row : d_->cell_map_) { @@ -384,7 +384,7 @@ row_t worksheet::get_highest_row() const column_t worksheet::get_highest_column() const { - column_t highest = constants::MinColumn(); + column_t highest = constants::min_column(); for (auto &row : d_->cell_map_) {