Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
137 changes: 119 additions & 18 deletions src/energyplus/ReverseTranslator/ReverseTranslateScheduleCompact.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -7,14 +7,29 @@

#include "../../model/ScheduleCompact.hpp"
#include "../../model/ScheduleCompact_Impl.hpp"
#include "../../model/ScheduleInterval.hpp"
#include "../../model/ScheduleInterval_Impl.hpp"
#include "../../model/ScheduleFixedInterval.hpp"
#include "../../model/ScheduleFixedInterval_Impl.hpp"
#include "../../model/ScheduleVariableInterval.hpp"
#include "../../model/ScheduleVariableInterval_Impl.hpp"
#include "../../model/YearDescription.hpp"
#include "../../model/YearDescription_Impl.hpp"

#include "../../utilities/data/TimeSeries.hpp"

#include "../../utilities/idf/IdfExtensibleGroup.hpp"

#include <utilities/idd/Schedule_Compact_FieldEnums.hxx>
#include <utilities/idd/OS_Schedule_Compact_FieldEnums.hxx>
#include <utilities/idd/OS_Schedule_FixedInterval_FieldEnums.hxx>
#include <utilities/idd/OS_Schedule_VariableInterval_FieldEnums.hxx>
#include "../../utilities/idd/IddEnums.hpp"
#include <utilities/idd/IddEnums.hxx>

#include "../../utilities/time/Date.hpp"
#include "../../utilities/core/ASCIIStrings.hpp"

using namespace openstudio::model;

namespace openstudio {
Expand All @@ -27,32 +42,118 @@ namespace energyplus {
return boost::none;
}

ScheduleCompact scheduleCompact(m_model);
std::vector<DateTime> dateTimes;
std::vector<double> values;

int day = 1; // temp
boost::optional<Date> date;
boost::optional<Time> time;
for (IdfExtensibleGroup& eg : workspaceObject.extensibleGroups()) {
for (unsigned i = 0; i < eg.numFields(); ++i) {
if (boost::optional<std::string> s = eg.getString(i)) {
std::string lower = openstudio::ascii_to_lower_copy(s.get());
if (lower.find("through") != std::string::npos) {
//date = lower;
date = Date(MonthOfYear(1), day); // temp
++day; // temp
} else if (lower.find("until") != std::string::npos) {
//time = lower;
//time = Time("24:00"); // temp
time = Time(0, 0, 0, 0);
}
}
if (date && time) {
DateTime datetime(*date, *time);
dateTimes.push_back(datetime);
date = boost::none;
time = boost::none;
}
if (boost::optional<double> value = eg.getDouble(i)) {
values.push_back(value.get());
}
}
}

boost::optional<Time> intervalLength;
intervalLength = Time(1, 0); // temp
bool forAllDays = true; // temp

if (intervalLength && forAllDays) {
Date startDateNoYear = dateTimes[0].date();
MonthOfYear monthOfYear = startDateNoYear.monthOfYear();
int dayOfMonth = startDateNoYear.dayOfMonth();
OS_ASSERT(dayOfMonth == 1);

model::YearDescription yd = m_model.getUniqueModelObject<model::YearDescription>();
Date startDate = yd.makeDate(monthOfYear, dayOfMonth);

OptionalWorkspaceObject target = workspaceObject.getTarget(Schedule_CompactFields::ScheduleTypeLimitsName);
if (target) {
OptionalModelObject scheduleTypeLimits = translateAndMapWorkspaceObject(*target);
if (scheduleTypeLimits) {
scheduleCompact.setPointer(OS_Schedule_CompactFields::ScheduleTypeLimitsName, scheduleTypeLimits->handle());
TimeSeries timeseries(startDate, *intervalLength, createVector(values), "");
boost::optional<ScheduleInterval> scheduleInterval = ScheduleInterval::fromTimeSeries(timeseries, m_model);
OS_ASSERT(scheduleInterval);
boost::optional<ScheduleFixedInterval> scheduleFixedInterval = scheduleInterval->optionalCast<ScheduleFixedInterval>();
OS_ASSERT(scheduleFixedInterval);

OptionalWorkspaceObject target = workspaceObject.getTarget(Schedule_CompactFields::ScheduleTypeLimitsName);
if (target) {
OptionalModelObject scheduleTypeLimits = translateAndMapWorkspaceObject(*target);
if (scheduleTypeLimits) {
scheduleFixedInterval->setPointer(OS_Schedule_FixedIntervalFields::ScheduleTypeLimitsName, scheduleTypeLimits->handle());
}
}
}

if (OptionalString os = workspaceObject.name()) {
scheduleCompact.setName(*os);
}
if (OptionalString os = workspaceObject.name()) {
scheduleFixedInterval->setName(*os);
}

for (IdfExtensibleGroup& eg : workspaceObject.extensibleGroups()) {
for (unsigned i = 0; i < eg.numFields(); ++i) {
if (auto value = eg.getString(i)) {
if (istringEqual(value.get(), "Interpolate:Average")) {
eg.setString(i, "Interpolate:Yes");
return scheduleFixedInterval.get();
} else if (forAllDays) {
TimeSeries timeseries(dateTimes, createVector(values), "");
boost::optional<ScheduleInterval> scheduleInterval = ScheduleInterval::fromTimeSeries(timeseries, m_model);
OS_ASSERT(scheduleInterval);
boost::optional<ScheduleVariableInterval> scheduleVariableInterval = scheduleInterval->optionalCast<ScheduleVariableInterval>();
OS_ASSERT(scheduleVariableInterval);

OptionalWorkspaceObject target = workspaceObject.getTarget(Schedule_CompactFields::ScheduleTypeLimitsName);
if (target) {
OptionalModelObject scheduleTypeLimits = translateAndMapWorkspaceObject(*target);
if (scheduleTypeLimits) {
scheduleVariableInterval->setPointer(OS_Schedule_VariableIntervalFields::ScheduleTypeLimitsName, scheduleTypeLimits->handle());
}
}

if (OptionalString os = workspaceObject.name()) {
scheduleVariableInterval->setName(*os);
}

return scheduleVariableInterval.get();
} else {
ScheduleCompact scheduleCompact(m_model);

OptionalWorkspaceObject target = workspaceObject.getTarget(Schedule_CompactFields::ScheduleTypeLimitsName);
if (target) {
OptionalModelObject scheduleTypeLimits = translateAndMapWorkspaceObject(*target);
if (scheduleTypeLimits) {
scheduleCompact.setPointer(OS_Schedule_CompactFields::ScheduleTypeLimitsName, scheduleTypeLimits->handle());
}
}

if (OptionalString os = workspaceObject.name()) {
scheduleCompact.setName(*os);
}

for (IdfExtensibleGroup& eg : workspaceObject.extensibleGroups()) {
for (unsigned i = 0; i < eg.numFields(); ++i) {
if (auto value = eg.getString(i)) {
if (istringEqual(value.get(), "Interpolate:Average")) {
eg.setString(i, "Interpolate:Yes");
}
}
}
scheduleCompact.pushExtensibleGroup(eg.fields());
}
scheduleCompact.pushExtensibleGroup(eg.fields());
}

return scheduleCompact;
return scheduleCompact;
}
}

} // namespace energyplus
Expand Down
58 changes: 58 additions & 0 deletions src/energyplus/Test/ScheduleInterval_GTest.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,8 @@
#include "../../utilities/time/Time.hpp"

#include "../../model/Model.hpp"
#include "../../model/ScheduleCompact.hpp"
#include "../../model/ScheduleCompact_Impl.hpp"
#include "../../model/ScheduleInterval.hpp"
#include "../../model/ScheduleInterval_Impl.hpp"
#include "../../model/ScheduleFixedInterval.hpp"
Expand Down Expand Up @@ -1991,3 +1993,59 @@ TEST_F(EnergyPlusFixture, ScheduleFileRelativePath) {
EXPECT_EQ(externalfile.filePath(), fileName.get());
}
}

void Run_RoundTrip_IDF_to_IDF(const std::string& filename, Workspace& w) {
w.save(filename + "_1.idf", true);

ReverseTranslator rt;
Model m = rt.translateWorkspace(w);

m.save(filename + "_2.osm", true);

EXPECT_EQ(0, m.getConcreteModelObjects<ScheduleCompact>().size());
EXPECT_EQ(1, m.getConcreteModelObjects<ScheduleFixedInterval>().size());
EXPECT_EQ(0, m.getConcreteModelObjects<ScheduleVariableInterval>().size());

ForwardTranslator ft;
Workspace w2 = ft.translateModel(m);

w2.save(filename + "_3.idf", true);

std::vector<WorkspaceObject> scheduleCompacts = w.getObjectsByType(IddObjectType::Schedule_Compact);
std::vector<WorkspaceObject> scheduleCompacts2 = w2.getObjectsByType(IddObjectType::Schedule_Compact);
EXPECT_EQ(scheduleCompacts.size(), scheduleCompacts2.size());

std::vector<WorkspaceObject> scheduleTypeLimitss = w.getObjectsByType(IddObjectType::ScheduleTypeLimits);
std::vector<WorkspaceObject> scheduleTypeLimitss2 = w2.getObjectsByType(IddObjectType::ScheduleTypeLimits);
EXPECT_EQ(scheduleTypeLimitss.size(), scheduleTypeLimitss2.size() - 3); // OnOff, OnOff 1, Fractional 1
}

TEST_F(EnergyPlusFixture, RoundTrip_IDF_ScheduleInterval) {
Workspace w(StrictnessLevel::Minimal, IddFileType::EnergyPlus);

IdfObject scheduleTypeLimits(openstudio::IddObjectType::ScheduleTypeLimits);
scheduleTypeLimits.setString(0, "Temperature");
scheduleTypeLimits.setString(3, "Continuous");
scheduleTypeLimits.setString(4, "temperature");

IdfObject scheduleCompact(openstudio::IddObjectType::Schedule_Compact);
scheduleCompact.setString(0, "mains temperature schedule");
scheduleCompact.setString(1, "Temperature");
scheduleCompact.setString(2, "Through: 01/01");
scheduleCompact.setString(3, "For: AllDays");
scheduleCompact.setString(4, "Until: 24:00");
scheduleCompact.setDouble(5, 10.0422222222222);
scheduleCompact.setString(6, "Through: 01/02");
scheduleCompact.setString(7, "For: AllDays");
scheduleCompact.setString(8, "Until: 24:00");
scheduleCompact.setDouble(9, 9.98111111111111);
scheduleCompact.setString(10, "Through: 01/03");
scheduleCompact.setString(11, "For: AllDays");
scheduleCompact.setString(12, "Until: 24:00");
scheduleCompact.setDouble(13, 9.92111111111111);

w.addObject(scheduleTypeLimits);
w.addObject(scheduleCompact);

Run_RoundTrip_IDF_to_IDF("RoundTrip_ScheduleFixedInterval", w);
}
2 changes: 1 addition & 1 deletion src/epmodel/Loop/Loop.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ namespace openstudio {
class AppGFuelType;
class ComponentType;
class FuelType;
class IddObjectType;
struct IddObjectType;
class IdfObject;

namespace epmodel {
Expand Down