Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Using records for providing pump parameters #209

Closed
Mathadon opened this issue Apr 12, 2014 · 43 comments
Closed

Using records for providing pump parameters #209

Mathadon opened this issue Apr 12, 2014 · 43 comments

Comments

@Mathadon
Copy link
Contributor

Hi Michael,

during the Annex60 meeting we discussed the possibility for using records to insert the parameters of a pump model. This way no documentation is 'lost' when extending a model. Also it makes switching between pumps easier.

I have made an implementation for this but it still needs some cleaning of the code. If you still think this is a good idea I'll put some work into it and make a pull request?

Best regards,

Filip

@mwetter
Copy link
Member

mwetter commented Apr 14, 2014

Hi Filip

I think using records would be a good addition for the Fluids.Movers package. A possible design could be to have

Fluids
  - Movers
  - Data
    - Pumps
    - Fans

where Pumps and Fans are packages with data records for different manufacturers. The user should then be able to select a record that contains all data needed for this fan or pump.

I made a development branch https://github.com/lbl-srg/modelica-buildings/tree/issue209_pumpRecords, please make any pull request to this branch so we can iterate on the implementation before putting it on the master.

We did a similar implementation in Buildings.Fluid.SolarCollectors.Data

@mwetter
Copy link
Member

mwetter commented Apr 17, 2014

@Mathadon reported:
I added the record and two examples. I documented one of the examples. The other example refers to the documentation of the first example.
The pump now by default uses the record 'PumpData' to get its parameters instead of using regular default values. This however seems to cause problems because these defaults cannot be overridden anymore. For example:

Check of Buildings.Fluid.Movers.Examples.FlowMachine_Nrpm:

Record has a value, and attempt to modify specific elements.
The element modification of e.g. V_flow will be ignored.
Modelica Text: near line 7
Attempted overriding found at:
Modelica Text: line 7

I do not know a solution for this.

I'll add more examples based on any feedback.

Also, I suppose an example similar to issue #202 is in order?

@mwetter
Copy link
Member

mwetter commented Apr 18, 2014

I looked at your pull request #211. I merged it to the development branch issue209_pumpRecords (only final changes are merged to the master).
The error is caused because Buildings.Fluid.Movers.Examples.FlowMachine_Nrpm assigns a record for the pressure. If we use a record that contains all pump/fan data, then Buildings.Fluid.Movers.Examples.FlowMachine_Nrpm should only have to assign values to this record. The model Buildings.Fluid.Movers.FlowMachine_Nrpm (or an appropriate base class) should then assign values from this record to other records (such as power, if this is still needed) or the functions that are used in the model. My initial guess is that records such as power can be removed, as all this data will be in pumpData, which should simply be called data as it is also used or fans.

@Mathadon
Copy link
Contributor Author

Woops, sorry for the wrong pull request.

I don't think the power record can be removed because you still need it if you want to override an individual parameter.

mwetter added a commit that referenced this issue Apr 21, 2014
This is for #209. Merged pull requests to development branch. Changed MoverData.mo to Generic.mo as the data package is already a sub-package of Movers.
mwetter added a commit that referenced this issue Apr 21, 2014
This is for #209. Now, performance data are only declared once, in the record called data. This record has been renamed from moverData to data because it is instantiated in the mover model, hence we can drop the name Mover. All unit tests give the same results.
mwetter added a commit that referenced this issue Apr 21, 2014
mwetter added a commit that referenced this issue Apr 21, 2014
mwetter added a commit that referenced this issue Apr 21, 2014
mwetter added a commit that referenced this issue Apr 22, 2014
This is for #209. The change was made to use a naming that is consistent with the chiller and the solar collector models, and also because data is too generic a name.
mwetter added a commit that referenced this issue Apr 22, 2014
This is for #209. The change was made to use a naming that is consistent with the chiller and the solar collector models, and also because data is too generic a name.
mwetter added a commit that referenced this issue Apr 22, 2014
This is for #209. The change was made to use a naming that is consistent with the chiller and the solar collector models, and also because data is too generic a name.
mwetter added a commit that referenced this issue Apr 22, 2014
@mwetter
Copy link
Member

mwetter commented Apr 24, 2014

@Mathadon : Looking at
http://productfinder.wilo.com/en/COM/product/0000000e000379df0002003a/fc_product_datasheet
I don't understand

record Stratos25slash1to4 "Pump data for a Wilo Stratos 25/1-4 pump"
  extends Generic(
    N_nominal=1800,
    N_min=1400,
    N_max=2800,
...

Wouldn't it be better to remove N_max, and set N_nominal=2800? Where do the N_nominal=1800 come from?

@Mathadon
Copy link
Contributor Author

@mwetter I agree that this is counter-intuitive. The reason is that most pump curves are 'interrupted' by the boundary you can see on the graph. To be able to apply similarity laws to the curve it must be 'complete'. The first curve that is not interrupted is the curve of 1800 rpm. Setting N_nominal to N_max would mean that the pump curves needs to be rescaled manually or that the pump model handles this properly.

Note that for this pump this is a very extreme example with a big difference between N_nominal and N_max. I have documented Buildings.Fluid.Movers.Data.Pumps.Stratos25slash1to6 where this difference is less extreme. In that model I also explain why that curve is chosen.

Is it necessary to add the datasheets as a pdf to the library?

@mwetter
Copy link
Member

mwetter commented Apr 25, 2014

@Mathadon : Please don't include the pdfs of the data sheets, as these may be copyright by the manufacturer and we may not be allowed to distribute them.

Regarding the N_max and N_nominal, the data sheet limits the maximum power. So, what seems to happen is that the pump curve follows the similarity laws everywhere, but the frequency controller limits the speed in such a way that the power consumption does not exceed a certain value. This is what probably causes this cut-off. I am not sure how to best address this in a way that makes sense also for other pumps. How do the pump and fan curves of other manufacturers look like? Is this an effect that only Wilo has?

@Mathadon
Copy link
Contributor Author

I do not know how this is usually handled. I googled some other brands/types:
A Grundfos pump with a maximum characteristic similar to Wilo:
http://net.grundfos.com/Appl/WebCAPS/Grundfosliterature-4352964.pdf
A pump with a bit different maximum curve:
http://www.lowara.com/lowdata/doc/EN/aflc-td-en.pdf
A wilo pump without maximum curve:
http://productfinder.wilo.com/nl/BE/product/0000001700017cd40003003a/fc_product_datasheet

Note that it is not power consumption that is limited as this would result in a hyperbolic curve. A maximum current may be more logical since thermal losses are proportional to the square of the current.

Another way to handle this would be by adding a 'maximum load curve' in the model.

@mwetter
Copy link
Member

mwetter commented Apr 30, 2014

It looks like we should add an optional maximum pressure raise curve to the pump data, and then restrict in FlowMachineInterface the value of dpMachine.
This probably will need to be done by modifying Characteristics.pressure() and using regularization to limit the maximum performance.
This maximum pressure raise needs to be modified so that

dp := dp - V_flow*kRes

reproduces the maximum pressure raise specified by the parameter.

This change also requires modifications to FlowMachineInterface.mo, in particular the initial algorithm section, as the computations that are now done for pCur? need also be done for this maximum pressure raise. Most of the computations in the initial algorithm section will need to be put into functions so that the code can be applied to both pressure raise curves.

@Mathadon
Copy link
Contributor Author

Mathadon commented May 2, 2014

That indeed sounds like the most robust solution. Do you want to implement this as a separate issue or continue working in #209 ?

@mwetter
Copy link
Member

mwetter commented May 2, 2014

It's probably best to make a separate branch for this that branches off from issue209_pumpRecords. That will make it easier to keep track of the changes.

@Mathadon
Copy link
Contributor Author

Can the current issue be merged before continuing with the maximum pressure raise curve?

@mwetter
Copy link
Member

mwetter commented May 27, 2014

I suggest to make a new branch off from issue209_pumpRecords. We plan to issue a new release (1.6) soon, and I think it may be better to release the pumps with records together with the maximum pressure raise curve to avoid too many changes to existing models. Hence, I suggest to schedule this for release 1.7 latter this summer.
I am not yet sure whether we can make this change backwards compatible, i.e, provide all conversions in https://github.com/lbl-srg/modelica-buildings/blob/issue209_pumpRecords/Buildings/Resources/Scripts/Dymola/ConvertBuildings_from_1.5_to_1.6.mos

@mwetter mwetter added this to the Release 1.7 milestone May 27, 2014
@Mathadon
Copy link
Contributor Author

Hi Michael,

FlowMachine_y currently contains the following code:

"Fan or pump with ideally controlled normalized speed y as input signal"
  extends Buildings.Fluid.Movers.BaseClasses.PrescribedFlowMachine(per(
  final N_nominal =    1500 "fix N_nominal as it is used only for scaling"))

When using the same 'per' record for a FlowMachine_y pump as for a FlowMachine_Nrpm pump this final N_nominal generates a warning since the per record already contains a value for N_nominal.

Overriding final modifier for N_nominal.
File: /media/psf/Home/Documents/Doctoraat/Software/Buildings-git/Buildings/Fluid/Movers/FlowMachine_y.mo, line 5

I suggest to remove the 'final' or remove the default value altogether and since it is already defined in Buildings.Fluid.Movers.Data.Generic?

Additionally the model contains:

Modelica.Blocks.Interfaces.RealInput y(min=0, max=1, unit="1") 

I think the 'max' value should not be equal to 1 since the pump characteristic may be defined for a different rpm than the maximum rpm. I suggest to either:

  1. remove this max value
  2. Set gaiSpe.k = per.N_max
  3. Set max=per.N_max/N_nominal.
    Also for clarity it may be better to rename N_nominal in per to something like N_curve to indicate that this is the rpm at which the pump curve was defined.

If you agree I can implement these changes if you like.

@mwetter
Copy link
Member

mwetter commented Jun 15, 2014

Hi Filip
I suggest you change

extends Buildings.Fluid.Movers.BaseClasses.PrescribedFlowMachine(per(
  final N_nominal =    1500 "fix N_nominal as it is used only for scaling"))

to

extends Buildings.Fluid.Movers.BaseClasses.PrescribedFlowMachine

and set a value for N_nominal in the record for performance data.

I agree that the max value should not be 1 as it can exceed this value.
Setting max=per.N_max/N_nominal is fine, although I think it should be max=per.N_max/per.N_nominal.

I would rather use N_nominal than N_curve, as the library uses performance data always for the operating point defined by *_nominal. Hence, I think suddenly introducing *_curve may confuse users.

@Mathadon
Copy link
Contributor Author

Ok, I'll implement this.

Another issue: I get the following warning when checking a model using the new pumps:

The parameter per.pressure.V_flow has some elements
per.pressure.V_flow[2]

which were fixed to constants,
since they control structural properties such as sizes of arrays.

Changing the 'parameters' in the 'generic' pump/fan records to 'constants' removes this warning. To remove the warning it is only necessary to make the pressure curve a constant. However I assume all parameters in the generic record can be set to constants?

mwetter added a commit that referenced this issue Jun 17, 2014
@mwetter
Copy link
Member

mwetter commented Oct 1, 2014

The efficiency currently only depends on r_V. I therefore don't understand
what you mean by " changing the pressure curve's values will rescale the
efficiency curve". I think such analysis would be better done in a report
so it is clear what assumptions or scenarios are beyond such assertions.
Using only the issue tracker risks that we don't mean the same and hence
misunderstand suggestions and go down a wrong path. I therefore suggest to
first work out the equations formally, and then talk about their
implementation in Modelica. This typically takes much less time and leads
to better code.

Setting V_flow_max = max(pressure.V_flow) is not good. I suggest to
extrapolate using the derivative and the last support point, which are
known in the model.
Records cannot have an equation section, but you can do some computations
when declaring the variables. See for example the HeatTransfer.Data.

On Tue, Sep 30, 2014 at 11:25 PM, Filip notifications@github.com wrote:

Can V_flow_max be computed inside the record?

I'm not aware of how design happens in practice so I will not argue on
this point but in my opinion using r_V for efficiency and V_flow for
pressure curve is a bit inconsistent. I also think it can be dangerous
because changing the pressure curve's values will rescale the efficiency
curve as well, although this seems to be your intention. It would seem more
intuitive to me that these two curves are decoupled.

If we use r_V then V_flow_max should be computed inside the mover record
to be able to convert the power curve into the efficiency curve. This way
it is also trivial to have consistency with FlowMachineInterface. The only
problem seems that V_flow_max depends on whether extrapolation is used at
dp=0 or if the last point on the pressure curve is considered to be the
maximum. This is not known in the record.
So we could set V_flow_max = max(pressure.V_flow) arbitrarily and have r_V

1 for dp = 0? Otherwise I'm afraid things will get a bit complicated.


Reply to this email directly or view it on GitHub
#209 (comment)
.

@Mathadon
Copy link
Contributor Author

Mathadon commented Oct 2, 2014

The efficiency currently only depends on r_V. I therefore don't understand
what you mean by " changing the pressure curve's values will rescale the
efficiency curve".

r_V is a function of V_flow_max, which is (or will be) a function of the pressure curve. Therefore changing the pressure curve will change the efficiency of the pump.

Setting V_flow_max = max(pressure.V_flow) is not good. I suggest to
extrapolate using the derivative and the last support point, which are
known in the model.

However, it is not known in the mover record, where I would like to calculate the efficiency.

Records cannot have an equation section, but you can do some computations
when declaring the variables. See for example the HeatTransfer.Data.

Yes indeed, that's what I did:

final parameter Real d[:] = if ( size(power.V_flow, 1) == 1)  then 
       {0}
   else 
      Buildings.Utilities.Math.Functions.splineDerivatives(
      x=power.V_flow,
      y=power.P,
      ensureMonotonicity=Buildings.Utilities.Math.Functions.isMonotonic(x=power.V_flow,
                                                                        strict=false));
Buildings.Fluid.Movers.BaseClasses.Characteristics.efficiencyParameters
    efficiency(V_flow=pressure.V_flow, eta=pressure.V_flow.*pressure.dp./
    {Buildings.Fluid.Movers.BaseClasses.Characteristics.power(per=power, V_flow=i, r_N=1, delta=0.01, d=d) for i in pressure.V_flow});

This implementation works, but uses V_flow instead of r_V since V_flow_max is not known in the record. Using r_V is impossible without moving it over.

Having elaborate discussions in an issue may indeed not be the best way to proceed. However writing reports is time-consuming and in this case I have provided a working implementation so I hope this can serve as sufficient grounds for discussion. Feel free to make changes directly in the code if you do not agree with some details?

@Mathadon
Copy link
Contributor Author

Mathadon commented Oct 7, 2014

Actually Buildings.Fluid.Movers.FlowMachine_dp2 seems to have some problems when switching in a discrete way: the non-linear iteration for r_N diverges due to the bad initial guess. I think I know how to solve this but it is probably best to keep this until other things are sorted out.

mwetter added a commit that referenced this issue Oct 8, 2014
@mwetter
Copy link
Member

mwetter commented Oct 9, 2014

This summarizes todays web-conference with @Mathadon:

  • Remove FlowMachine_dp2 from the development branch as this requires an iterative solution to solve for the speed r_N. Such a detailed flow machine could be added later when the first revision is done.
  • Without solving for N, the power consumption is an approximation for some models. Add an explicit note to these models that informs the user, and use PumpCrossValidation to show the difference in results. (This model should be called CrossValidation as it is also applicable to fans and it already is in a subdirectory of FlowMachine).
  • For the performance curves pressure, power, hydraulicEfficiency and motorEfficiency, use V_flow as the independent parameter, rather than r_V.
    If V_max_flow where needed in the record (which I believe it is not), it could be propagated as follows:
In Data/Generic.mo, write
parameter Modelica.SIunits.VolumeFlowRate V_flow_max "Maximum volume flow rate";

In BaseClasses/PowerInterface.mo, use
  replaceable parameter Data.Generic per constrainedby Data.Generic(V_flow_max=V_flow_max) 
    "Record with performance data" annotation (choicesAllMatching=true,
      Placement(transformation(extent={{60,-80},{80,-60}})));
  • Remove from Data.Generic any paramaters that are not needed. In particular efficiency and I believe N_min and N_max.
  • In Data.Generic remove any default values that are not generally applicable (such as volume flow rate).
  • To allow an easily scaling of the models for large flow rates (at the same pressure), models should have a parameter
parameter Real scale_m_flow(min=0) = 1 "Scaling factor for mass flow rate"

This should allow scaling the fan/pump to a larger or smaller volume flow rate so that if scale_m_flow=2 (and the pressure raise is the same), then the fan uses twice as much power and has twice the volume flow rate.

  • For backward compatibility, copy the old FlowMachine back to Obsolete.Movers and provide a conversion script.
  • Update/revise the UserGuide and the info sections of the models as needed to reflect the changes.
  • Lastly, copy the new package to the Annex60 library for review and inclusion.

@Mathadon
Copy link
Contributor Author

minand max were apparently currently being used:

Modelica.Blocks.Interfaces.RealInput Nrpm(unit="1/min", min=per.N_min, max=per.N_max)

I removed them.

@Mathadon
Copy link
Contributor Author

I addressed points 1 through 5 except for any changes involving documentation in point 2.
https://github.com/Mathadon/modelica-buildings/tree/issue209_202_pumprecords

mwetter added a commit that referenced this issue Nov 23, 2014
mwetter added a commit that referenced this issue Nov 23, 2014
mwetter added a commit that referenced this issue Nov 23, 2014
For #209. This restructuring is required to avoid that mover data require the user to enter data that are not used by the model. Using default values such as V_flow={0} does not work as this lead to a division by zero in some model. Also, not declaring a default value also does not work as this led to error such as 'Failed to expand the variable floMacSta.per.pressure.V_flow'. Therefore, the package has been redesigned so that only the minimum set of required data need to be entered. See also the updated user's guide.
mwetter added a commit that referenced this issue Nov 23, 2014
This was needed because the efficiency function of the movers can no longer be used.
@mwetter
Copy link
Member

mwetter commented Nov 23, 2014

@Mathadon :
Should we remove Buildings.Fluid.Movers.Examples.FlowMachine_Nrpm_stratos?
I think this is a similar test than FlowMachine_Stratos. If you think we should keep it, can you please address the fixme and make sure all components have a documentation. Otherwise I probably remove it.
Note that there are a lot of changes on this branch, so please merge to your branch before editing.

mwetter added a commit that referenced this issue Nov 24, 2014
@Mathadon
Copy link
Contributor Author

@mwetter I used that model to generate the picture below:

pumphead2validationresult

this picture can serve as a validation for the pump model. If you include it in the library then this model may be a good reference to show where the result came from?

If this is not of interest then feel free to remove it!

@mwetter
Copy link
Member

mwetter commented Nov 26, 2014

@Mathadon Can you please include the figure in the example and document the example (see my previous note). This would be useful for users.
It takes much more time for me to figure out what you did and document it as opposed for you to finish your models to a point where they are ready for inclusion. I rather use that time to address the other open points and look again at the restructuring I needed to do for the records.

@Mathadon
Copy link
Contributor Author

Of course, no problem

@Mathadon
Copy link
Contributor Author

The background of the figure above is from a data sheet. You mentioned before that this may be a problem (copyright/IP issue?). Is this still the case?

@mwetter
Copy link
Member

mwetter commented Nov 26, 2014

I think for this case it is OK. Best would be to write "Figure adapted from
xxx"

On Wed, Nov 26, 2014 at 10:09 AM, Filip notifications@github.com wrote:

The background of the figure above is from a data sheet. You mentioned
before that this may be a problem (copyright/IP issue?). Is this still the
case?


Reply to this email directly or view it on GitHub
#209 (comment)
.

mwetter added a commit that referenced this issue Dec 3, 2014
mwetter added a commit that referenced this issue Dec 4, 2014
@mwetter
Copy link
Member

mwetter commented Dec 4, 2014

@Mathadon : Can you please add the documentation regarding Buildings.Fluid.Movers.Examples.FlowMachine_Nrpm_stratos. Note that this model is now
Buildings.Fluid.Movers.Validation.Pump_Nrpm_stratos.
I updated the names of all movers so that they are either FlowControlled if they use m_flow or dp as a signal, or SpeedControlled if they use y or Nrpm as an input signal.

I also move some examples to the Validation package.

This is now close to complete so that we can move it to the master and also the Annex60 repository.

These are the renames I did:

import buildingspy.development.refactor as r
import os

r.move_class("Buildings.Fluid.Movers.Examples.BaseClasses.ControlledFlowMachine",
             "Buildings.Fluid.Movers.Validation.BaseClasses.ControlledFlowMachine")

r.move_class("Buildings.Fluid.Movers.FlowMachine_dp",
             "Buildings.Fluid.Movers.FlowControlled_dp")
r.move_class("Buildings.Fluid.Movers.FlowMachine_m_flow",
             "Buildings.Fluid.Movers.FlowControlled_m_flow")
r.move_class("Buildings.Fluid.Movers.FlowMachine_Nrpm",
             "Buildings.Fluid.Movers.SpeedControlled_Nrpm")
r.move_class("Buildings.Fluid.Movers.FlowMachine_y",
             "Buildings.Fluid.Movers.SpeedControlled_y")
r.move_class("Buildings.Fluid.Movers.Examples.FlowMachine_dp",
             "Buildings.Fluid.Movers.Validation.FlowControlled_dp")
r.move_class("Buildings.Fluid.Movers.Examples.FlowMachine_m_flow",
             "Buildings.Fluid.Movers.Validation.FlowControlled_m_flow")
r.move_class("Buildings.Fluid.Movers.Examples.FlowMachine_Nrpm",
             "Buildings.Fluid.Movers.Validation.SpeedControlled_Nrpm")
r.move_class("Buildings.Fluid.Movers.Examples.FlowMachine_Nrpm_stratos",
             "Buildings.Fluid.Movers.Validation.Pump_Nrpm_stratos")
r.move_class("Buildings.Fluid.Movers.Examples.FlowMachine_Stratos",
             "Buildings.Fluid.Movers.Validation.Pump_stratos")
r.move_class("Buildings.Fluid.Movers.Examples.FlowMachine_y",
             "Buildings.Fluid.Movers.Validation.SpeedControlled_y")
r.move_class("Buildings.Fluid.Movers.Examples.FlowMachine_y_linear",
             "Buildings.Fluid.Movers.Validation.SpeedControlled_y_linear")
r.move_class("Buildings.Fluid.Movers.Examples.FlowMachine_y_pumpCurves",
             "Buildings.Fluid.Movers.Examples.SpeedControlled_y_pumpCurves")
r.move_class("Buildings.Fluid.Movers.Examples.FlowMachineFeedbackControl",
             "Buildings.Fluid.Movers.Examples.ClosedLoop_y")
r.move_class("Buildings.Fluid.Movers.Examples.FlowMachineParallel_y",
             "Buildings.Fluid.Movers.Examples.PumpsParallel")
r.move_class("Buildings.Fluid.Movers.Examples.FlowMachineSeries_y",
             "Buildings.Fluid.Movers.Examples.PumpsSeries")
r.move_class("Buildings.Fluid.Movers.Examples.ControlledFlowMachine",
             "Buildings.Fluid.Movers.Validation.ControlledFlowMachine")
r.move_class("Buildings.Fluid.Movers.Examples.ControlledFlowMachineDynamic",
             "Buildings.Fluid.Movers.Validation.ControlledFlowMachineDynamic")
r.move_class("Buildings.Fluid.Movers.Examples.CrossValidation",
             "Buildings.Fluid.Movers.Validation.Power")

@Mathadon
Copy link
Contributor Author

Mathadon commented Dec 8, 2014

I think I addressed the documentation in #322 ?

@mwetter
Copy link
Member

mwetter commented Dec 12, 2014

This is now on the master branch

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants