-
Notifications
You must be signed in to change notification settings - Fork 208
New issue
Have a question about this project? # for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “#”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? # to your account
Addresses #4223, wrap the new ElectricLoadCenter:Storage:LiIonNMCBattery object in the OS SDK #4225
Conversation
357511a
to
94f63bd
Compare
LGTM, I suggest merging @kbenne |
// Number of Cells in Series | ||
i = workspaceObject.getInt(ElectricLoadCenter_Storage_LiIonNMCBatteryFields::NumberofCellsinSeries); | ||
OS_ASSERT(i); | ||
const int nSeries = *i; | ||
|
||
// Number of Strings in Parallel | ||
i = workspaceObject.getInt(ElectricLoadCenter_Storage_LiIonNMCBatteryFields::NumberofStringsinParallel); | ||
OS_ASSERT(i); | ||
const int nParallel = *i; | ||
|
||
// Battery Mass | ||
d = workspaceObject.getDouble(ElectricLoadCenter_Storage_LiIonNMCBatteryFields::BatteryMass); | ||
OS_ASSERT(d); | ||
const double mass = *d; | ||
|
||
// Battery Surface Area | ||
d = workspaceObject.getDouble(ElectricLoadCenter_Storage_LiIonNMCBatteryFields::BatterySurfaceArea); | ||
OS_ASSERT(d); | ||
const double surfaceArea = *d; | ||
|
||
openstudio::model::ElectricLoadCenterStorageLiIonNMCBattery elcStorLiIonNMCBattery(m_model, nSeries, nParallel, mass, surfaceArea); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@joseph-robertson I made these changes to get the fields we need to construct the object before doing so. Because they're required, I'm no longer doing the if(i) ...
before setting it because it needs to be there. Is using OS_ASSERT
a good way to do that here, or do I need to have it return a more gentle error message?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'd say follow this as an example: https://github.com/NREL/OpenStudio/blob/develop/src/energyplus/ReverseTranslator/ReverseTranslateSurfaceControlMovableInsulation.cpp. Both surface
and material
are passed into the ctor.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I still want to try to come up with an additional alternative constructor and possibly a setter or two that takes more user-friendly inputs like "target battery capacity [kwh]" and generates some of the other inputs like series and parallel from that. However, if we need to merge this sooner, I'm fine with this the way it is and I'll do that in a later version or in our measure code.
explicit ElectricLoadCenterStorageLiIonNMCBattery(const Model& model, const int numberofCellsinSeries, const int numberofStringsinParallel, | ||
const double batteryMass, const double batterySurfaceArea); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I changed the constructor to require these additional fields.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not a big fan of this change. If we can provide reasonable defaults (I think we can, just pick whatever is in your E+ example file) I'd prefer to have a ElectricLoadCenterStorageLiIonNMCBattery(const Model& model)
ctor.
You can have 2 constructors if you want this explicit one. And you could still throw in the ReverseTranslator if the IDF doesn't have one of these fields if you like (or issue a Warn/Error, and let the default pass in)
(This isn't "out the blue", we've had lengthy discussions about this in the past).
@joseph-robertson Do you know what's going wrong with the windows incremental build? |
MSVC is throwing because of your RT:
( I fixed this in b194c95 and did a little change while I was at in in 24d3eb2 |
Ok, now Windows reports a failure that you can ignore, it's a know ruby test that's failing
|
I would personally like an alternative, model only, ctor. I'm fine with the rest. @kbenne thoughts? |
I also prefer that ModelObject constructors offer one overload that requires only a model argument. Nothing wrong with other more explicit overloads, but I feel like the simple construction with one argument makes the API more approachable. |
@jmarrec @kbenne I intentionally removed the "model only" constructor because I felt like some fields should be provided by the user. The additional constructor I am thinking of adding is one that will calculate the number of series and parallel based on a desired capacity. I'm worried that a user will just use the default constructor and assume that it's a good model, when it's not. Maybe I'm not understanding the paradigm of how the OpenStudio API should work. |
Upon further consideration, I think I'm going to wait until the next release to add another constructor with the capacity that calculates the series and parallel. There's still some logic we need to figure out on what should be defaulted and how that will work in practice. As far as I'm concerned, I'm happy with this the way it is to merge, so don't wait on me. I'm headed out of town next week and won't be able to work on this, so if you feel very strongly that it needs a model only constructor, please go ahead and put it back in. Thanks for being patient with me on this. |
@nmerket I totally understand your initial point of view on this, but I'll try to provide some insight as to why I think differently. I think providing a Ctor that takes the required argument(s) is fine and helps drive the point that they should be provided. But I still want a Ctor that takes
The reason is because it's much harder to use the API if you don't. When I need to write a measure or some code, I jump into an interactive ruby prompt (via In your specific case, you're trying to require numeric fields. Most objects in the API have double/integer/choice fields that must be tweaked in order to produce realistic results (or just because they are marked DetailsSome Demonstration on my API usage, click to expandMost of the time, I can construct an object [1] julien(main)> include OpenStudio::Model
=> Object
[2] julien(main)> m = Model.new
=> #<OpenStudio::Model::Model:0x000055b4845e08d8
@__swigtype__="_p_openstudio__model__Model">
[3] julien(main)> b = BoilerHotWater.new(m)
=> #<OpenStudio::Model::BoilerHotWater:0x000055b4840b3450 Sometimes it doesn't work, but I can trick ruby (well, SWIG to be exact) into giving me more info by passing bogus args, and I get enough info to go on (eg: below, from domain knowledge and argument type, I know it's the [6] julien(main)> atu = AirTerminalSingleDuctConstantVolumeNoReheat.new(m)
ArgumentError: wrong # of arguments(1 for 2)
from (pry):6:in `initialize'
# Pass bogus arg
[7] julien(main)> atu = AirTerminalSingleDuctConstantVolumeNoReheat.new(m, "")
TypeError: Expected argument 1 of type openstudio::model::Schedule &, but got String ""
in SWIG method 'AirTerminalSingleDuctConstantVolumeNoReheat'
from (pry):7:in `initialize' Now, what happens when you provide a Ctor that needs a lot of arguments, and with the same type for different args? Well, there is no way other than to go to the SDK documentation to look it up, which is clumsy and makes you lose time. [8] julien(main)> ptac = ZoneHVACPackagedTerminalAirConditioner.new(m)
ArgumentError: wrong # of arguments(1 for 5)
from (pry):8:in `initialize'
[9] julien(main)> ptac = ZoneHVACPackagedTerminalAirConditioner.new(m, "", "", "", "")
TypeError: Expected argument 1 of type openstudio::model::Schedule &, but got String ""
in SWIG method 'ZoneHVACPackagedTerminalAirConditioner'
from (pry):9:in `initialize'
[10] julien(main)> ptac = ZoneHVACPackagedTerminalAirConditioner.new(m, m.alwaysOnDiscreteSchedule, "", "", "")
TypeError: Expected argument 2 of type openstudio::model::HVACComponent &, but got String ""
in SWIG method 'ZoneHVACPackagedTerminalAirConditioner'
# At this point I know it's expecting either the Fan, the Heating COil or the Cooling coil, which one is it?! I need several clicks to get here: https://openstudio-sdk-documentation.s3.amazonaws.com/cpp/OpenStudio-3.1.0-doc/model/html/classopenstudio_1_1model_1_1_zone_h_v_a_c_packaged_terminal_air_conditioner.html and even the signature isn't enough, I need an extra click until I see the arguments names Once I have the object, I can inspect it, look at its methods, etc [13] julien(main)> puts atu
OS:AirTerminal:SingleDuct:ConstantVolume:NoReheat,
{d12f35b0-b126-4a67-a928-d5e5e5eb8da8}, !- Handle
Air Terminal Single Duct Constant Volume No Reheat 1, !- Name
{b22711ff-fbcd-4967-8fe1-70b8c804d423}, !- Availability Schedule Name
, !- Air Inlet Node Name
, !- Air Outlet Node Name
AutoSize; !- Maximum Air Flow Rate {m3/s}
=> nil This is OpenStudio, so most of the time by looking at a field I can infer its corresponding getter/setter. [14] julien(main)> atu.methods.grep(/^set/)
=> [:setMaximumAirFlowRate,
:setAvailabilitySchedule,
:setParent,
:setPointer,
:setFieldComment,
:setString,
:setDouble,
:setQuantity,
:setComment,
:setUnsigned,
:setInt,
:setName] |
I put back a Model only ctor in 4096a0b. I left the (unusual in my opinion) ctor that takes numeric field in place though. |
CI Results for 278e228:
|
Pull request overview
Please read OpenStudio Pull Requests to better understand the OpenStudio Pull Request protocol.
Pull Request Author
Add to this list or remove from it as applicable. This is a simple templated set of guidelines.
src/model/test
)src/energyplus/Test
)src/osversion/VersionTranslator.cpp
)src/openstudio_lib/library/OpenStudioPolicy.xml
)Labels:
IDDChange
APIChange
Pull Request - Ready for CI
so that CI builds your PRReview Checklist
This will not be exhaustively relevant to every PR.