B u `0@sddlZddlmZddlmZmZddlmZmZm Z ddl m Z m Z m Z ddlmZddlmZddlmZdd lmZdd lmZdd lmZdd lmZmZmZmZed ZddZddZddZddZ ddZ!ddZ"ej#dddGdddeZ$dS)N) ComponentSet)TransformationTransformationFactory)Var Expression Objective) ContinuousSet DerivativeVarIntegral)generate_finite_elements)expand_components)create_partial_expression)add_discretization_equations)block_fully_discretized) DAE_Error) ConfigBlock ConfigValue PositiveIntInz pyomo.daecsfdd}|S)zZ Applies the Central Difference formula of order O(h^2) for first derivatives csbt}|d}|dkr&tdd||d||d||d||dS)Nrzlist index out of range)listord IndexError)itmpidx)svF/tmp/pip-unpacked-wheel-n62dbgi3/pyomo/dae/plugins/finitedifference.py_ctr_fun#s z$_central_transform.._ctr_funr)rrr r)rrr_central_transformsr!csfdd}|S)z[ Applies the Central Difference formula of order O(h^2) for second derivatives cst}|d}|dkr&tdd||d||||||d||dd||||dS)Nrrzlist index out of range)rrr)rrr)rrrr _ctr_fun22s *z,_central_transform_order2.._ctr_fun2r)rrr#r)rrr_central_transform_order2-sr$csfdd}|S)zT Applies the Forward Difference formula of order O(h) for first derivatives csJt}|d}d||d||||d||S)Nr)rr)rrr)rrrr_fwd_fun@sz$_forward_transform.._fwd_funr)rrr%r)rrr_forward_transform<sr&csfdd}|S)zU Applies the Forward Difference formula of order O(h) for second derivatives csvt}|d}d||d||d||d||||dd||d||S)Nrr")rr)rrr)rrrrr%Ks.z+_forward_transform_order2.._fwd_funr)rrr%r)rrr_forward_transform_order2Gsr'csfdd}|S)zU Applies the Backward Difference formula of order O(h) for first derivatives csZt}|d}|dkr&tdd||||d||||dS)Nrrzlist index out of range)rrr)rrr)rrrr_bwd_funXs z%_backward_transform.._bwd_funr)rrr(r)rrr_backward_transformTsr)csfdd}|S)zZ Applies the Backward Difference formula of order O(h) for second derivatives cst}|d}|dks&|dkr.tdd||d||d||||d||d||d||dS)Nrrzlist index out of ranger")rrr)rrr)rrrrr(fs .z,_backward_transform_order2.._bwd_funr)rrr(r)rrr_backward_transform_order2as r*zdae.finite_differencez\Discretizes a DAE model using a finite difference method transforming the model into an NLP.)docc seZdZdZedZedededdededd d d ed ed e d ddgdddfddZ ddZ ddZ Z S) Finite_Difference_Transformationz_ Transformation that applies finite difference methods to DAE, ODE, or PDE models. zdae.finite_differencenfe zPThe desired number of finite element points to be included in the discretization)defaultdomain descriptionwrtNz#The ContinuousSet to be discretizedzIndicates which ContinuousSet the transformation should be applied to. If this keyword argument is not specified then the same scheme will be applied to all ContinuousSets.)r/r1r+schemeBACKWARDCENTRALFORWARDz1Indicates which finite difference scheme to applyz_Options are BACKWARD, CENTRAL, or FORWARD. The default scheme is the backward difference method)r/r0r1r+cs2tt|i|_ttfttftt fd|_ dS)N)r4r5r6) superr,__init___nfer)r*r!r$r&r' all_schemes)self) __class__rrr8s z)Finite_Difference_Transformation.__init__cKs||}|j}|j}|dk rX|jtk r2tdn&d|krXtd|d|jfd|j krjtdt |j dkr|dkr||j d<d}n||j |j<|j}|j |_ |j |j d|_||||S)a Applies the transformation to a modeling instance Keyword Arguments: nfe The desired number of finite element points to be included in the discretization. wrt Indicates which ContinuousSet the transformation should be applied to. If this keyword argument is not specified then the same scheme will be applied to all ContinuousSets. scheme Indicates which finite difference method to apply. Options are BACKWARD, CENTRAL, or FORWARD. The default scheme is the backward difference method NzHThe component specified using the 'wrt' keyword must be a continuous setr3zQThe discretization scheme '%s' has already been applied to the ContinuousSet '%s'zA general discretization scheme has already been applied to to every continuous set in the model. If you would like to apply a different discretization scheme to each continuous set, you must declare a new transformation objectr)CONFIGr-r2ctyper TypeErrorget_discretization_info ValueErrornamer9lenr3 _scheme_namer:get_scheme_transformBlock)r;instancekwdsconfigZtmpnfeZtmpds currentdsrrr _apply_tos,          z*Finite_Difference_Transformation._apply_tocCsPi|_x|tD]}|dks0||jks0||krd|krJtd|jt||j||st |d|j|krt d|jt |d|j|j<t ||j|j<|}|j|j|d<|j d|d<qWt|x|jtddD]}|}xt|D]}|dks |j|kr|}|j|} ||} | d kr^td |j|jf|j| d} t| ||| } || qW|rt||||tt|d d} | dkrt |_|j} | |qWt!|rL|"t#rLx0|jt#ddD]}|$||t%qWx |jt&ddD]}|$q:WdS) Nr3zSAttempting to discretize ContinuousSet '%s' after it has already been discretized. rzMore finite elements were found in ContinuousSet '%s' than the number of finite elements specified in apply. The larger number of finite elements will be used.r-z DifferenceT)Z descend_intozError discretizing '%s' with respect to '%s'. Current implementation only allows for taking the first or second derivative with respect to a particular ContinuousSet&_pyomo_dae_reclassified_derivativevars)'Z_feZcomponent_objectsrrBr@rr r9Z get_changedrCloggerwarnrrDr r Zget_continuousset_listrZget_derivative_expressionZ get_state_varZ_contsetcountrFr Zset_derivative_expressionZis_fully_discretizedrZ parent_blockZreclassify_component_typergetattrrNappendrZcontains_componentr Z reconstructrr)r;blockrKZdsZ disc_infodZdsetsrZoldexprlocrQr3ZnewexprZreclassified_listkrrrrGsb         z0Finite_Difference_Transformation._transformBlock)__name__ __module__ __qualname____doc__rr=Zdeclarerrrr8rLrG __classcell__rr)r<rr,ss$     5r,)%loggingZpyomo.common.collectionsrZpyomo.core.baserrZ pyomo.corerrrZ pyomo.daerr r Zpyomo.dae.miscr r r rrZpyomo.dae.diffvarrZpyomo.common.configrrrr getLoggerrOr!r$r&r'r)r*registerr,rrrr s(