PSS/E fortran array modules - fortran

I am developing a user-written control model for an inverter in PSS/E through Fortran language. I want to link this control model to a standard generator model.
I've already check that the control model works fine. I am entering 2 input commands: Real Power (P) and Reactive Power (Q). I have check through internal variables that the model takes well these values defined by me. And the outputs of this control model are "correct" both outpus signals are what are supposed to be.
The problem is that I'm not be able to link it to the standard generator model. As this model is contained in an external .dll file I use the USE [MODULE] statement at the beginning of the code and in MODE 3 I just write:
WIPCMD1(MC)=VAR(L+5)
WIQCMD1(MC)=VAR(L+4)
Where MC is the machine index where apply both models, WIPCMD and WIQCMD are the arrays that work as input of the generator model and VAR(L+5) and VAR(L+4) are the outputs from my user-written control model.
I know that the connection is wrong because when I change the 2 inputs of the control model, the 2 outputs of this control change too, but the outputs of the generator model are always de same (I think that are the initialized ones from the power flow).
Another possible cause is that I am compiling wrong the files in the PSS/E Environment Manager: I just put the my control model .flx file inside "User Model Fortran Source Files" and the .obj file with the same name of the .mod file that contains the GEPVMODULE in "User Model Object, Library Files". I use the resultant .dll file.
Any idea? Bellow is the whole code of the .flx control model.
Thank you very much.
Regards
SUBROUTINE INVCTRLELEC (MC,ISLOT)
C
USE GEPVMODULE
C
$INSERT COMON4.INS
C
INTEGER I,J,K,L,MC,ISLOT,BS
INTEGER IERR1,IERR3
REAL VINP1,VINP2,VINP3,VINP4,VINP5,VINP6,VINP7,VINP8,VINP9,VINP10
REAL VOUT1,VOUT2,VOUT3,VOUT4,VOUT5,VOUT6,VOUT7,VOUT8,VOUT9,VOUT10
C
C
I=STRTIN(4,ISLOT)
J=STRTIN(1,ISLOT)
K=STRTIN(2,ISLOT)
L=STRTIN(3,ISLOT)
C
CALL FLOW1(I,L+6,L+1,L+7)
C
IF (MODE.EQ.8)
. CON_DSCRPT(1)='Kqi'
. CON_DSCRPT(2)='Kvi'
. CON_DSCRPT(3)='Ihql'
. CON_DSCRPT(4)='Ipmax'
. CON_DSCRPT(5)='Iphl'
. CON_DSCRPT(6)='Vmaxcl'
. CON_DSCRPT(7)='Vmincl'
. CON_DSCRPT(8)='Vdc'
. CON_DSCRPT(9)='Porder'
. CON_DSCRPT(10)='Qorder'
. ICON_DSCRPT(1)='Bus origen'
. ICON_DSCRPT(2)='Bus destino'
. ICON_DSCRPT(3)='Identificador'
. RETURN
...FIN
C
IF (MODE.GT.4) GO TO 1000
C
GO TO (100,200,300,400), MODE
C
100 VOUT1=CON(J+9)-VAR(L+1)
VINP1=INT_MODE1(1.0,VOUT1,K,IERR1)
C
VOUT3=VOUT2-VAR(L+2)
VINP3=INT_MODE1(1.0,VOUT3,K+1,IERR3)
VAR(L+2)=ABS(VOLT(ICON(I)))
C
VAR(L+5)=WIPCMD1(MC)
VAR(L+4)=WIQCMD1(MC)
C
RETURN
C
200 VAR(L+2)=ABS(VOLT(ICON(I)))
C
VINP1=CON(J+9)-VAR(L+1)
VOUT1=INT_MODE2(1.0,VINP1,K)
VAR(L)=CON(J+9)
C
VINP2=VOUT1*CON(J)
VOUT2=MIN(CON(J+5),MAX(CON(J+6),VINP2))
C
VINP3=VOUT2-VAR(L+2)
VOUT3=INT_MODE2(1.0,VINP3,K+1)
VAR(L+11)=VOUT3*CON(J+1)
C
VINP5=VAR(L+5)
VOUT5=((CON(J+3))**(2)-(VAR(L+5))**(2))**(0.5)
C
VINP6=VOUT5
VOUT6=MIN(CON(J+2),VINP6)
VAR(L+8)=VOUT6
C
VINP7=VAR(L+2)
VOUT7=-0.5+0.01733*(VINP7*360-360)-0.0117*(CON(J+7)-560)+VAR(L+6)*1/4.37
VAR(L+9)=VOUT7
C
VINP4=VOUT3*CON(J+1)
VOUT4=MIN(VOUT6,MAX((MAX(VOUT7,-VOUT6)),VINP4))
VAR(L+4)=VOUT4
C
VINP8=VAR(L+2)
VOUT8=MAX(0.01,VAR(L+2))
C
VINP9=CON(J+8)
VAR(L+3)=CON(J+8)
VOUT9=VINP9/VOUT8
C
VINP10=VOUT9
VOUT10=MIN(MIN(CON(J+3),CON(J+4)),VINP10)
VAR(L+5)=VOUT10
C
RETURN
C
300 VAR(L+2)=ABS(VOLT(ICON(I)))
C
VINP1=CON(J+9)-VAR(L+1)
VOUT1=INT_MODE3(1.0,VINP1,K)
VAR(L)=CON(J+9)
C
VINP2=VOUT1*CON(J)
VOUT2=MIN(CON(J+5),MAX(CON(J+6),VINP2))
C
VINP3=VOUT2-VAR(L+2)
VOUT3=INT_MODE3(1.0,VINP3,K+1)
VAR(L+11)=VOUT3*CON(J+1)
C
VINP5=VAR(L+5)
VOUT5=((CON(J+3))**(2)-(VAR(L+5))**(2))**(0.5)
C
VINP6=VOUT5
VOUT6=MIN(CON(J+2),VINP6)
VAR(L+8)=VOUT6
C
VINP7=VAR(L+2)
VOUT7=-0.5+0.01733*(VINP7*360-360)-0.0117*(CON(J+7)-560)+VAR(L+6)*1/4.37
VAR(L+9)=VOUT7
C
VINP4=VOUT3*CON(J+1)
VOUT4=MIN(VOUT6,MAX((MAX(VOUT7,-VOUT6)),VINP4))
VAR(L+4)=VOUT4
C
VINP8=VAR(L+2)
VOUT8=MAX(0.01,VAR(L+2))
C
VINP9=CON(J+8)
VAR(L+3)=CON(J+8)
VOUT9=VINP9/VOUT8
C
VINP10=VOUT9
VOUT10=MIN(MIN(CON(J+3),CON(J+4)),VINP10)
VAR(L+5)=VOUT10
C
WIPCMD1(MC)=VAR(L+5)
WIQCMD1(MC)=VAR(L+4)
C
VAR(L+12)=MC
VAR(L+13)=ISLOT
C
RETURN
C
400 NINTEG=MAX(NINTEG,K+3)
RETURN
C
IF (MODE.EQ.6) GO TO 2000
C
900 RETURN
1000 RETURN
2000 RETURN
RETURN
END

Related

Get Mbase (MVA) of Machine from PSSE for Python code

Please help me to get Mbase (MVA) of Machine from PSSE for Python.
I would like to use this to calculate with inertia (H) value.
Although I can get H as syntax below, I don't know how to get Mbase (MVA).
ierr = psspy.rwdy(option1=2,option2=0,out=0,ofile="C:\Program Files (x86)\PTI\PSSE34\EXAMPLE\python_test1.out")
21421 'GENROU' 1 11.000 0.47000E-01 0.67000 0.50000E-01 6.2300 0.0000 2.1000 1.5500 0.21000 0.40000 0.16000 0.13000 0.36100 0.69300
Thanks!
You can use psspy.macdat() as follows to store the value in a new variable mbase:
ierr, mbase = psspy.macdat(
ibus=bus_number, # bus number where machine is connected as an `int` object
id=id_, # machine ID as a `str` object
string='MBASE',
)
You will of course need to have already defined bus_number and id_.
You may see the other options by reading the docstring:
import psse34
import psspy
help(psspy.macdat)
Thank you for your support.
Based on your introduction, I can get Mbase.
Due to a lot of machines, so I have to use for loop in order to get all of the power data of machines. Please give me some advice whether there is any other way than to use a for loop.
Please see the picture result on Notepad++
enter image description here
That's so kind of you.
import psse34
import psspy
# Last case:
CASE = r"C:\Program Files (x86)\PTI\PSSE34\EXAMPLE\savnw.sav"
psspy.psseinit(12000)
psspy.case(CASE)
ierr = psspy.dyre_add(dyrefile="C:\Program Files (x86)\PTI\PSSE34\EXAMPLE\savnw.dyr")
ierr = psspy.rstr("C:\Program Files (x86)\PTI\PSSE34\EXAMPLE\savnw.snp")
ierr = psspy.rwdy(1,1,ofile="C:\Program Files (x86)\PTI\PSSE34\EXAMPLE\python_test1.out") # find inertia (H) of machine
machine1=[101,102,206,211,3011,3018]
for x in machine1:
ierr, mbase = psspy.macdat(ibus=x, id='1', string='MBASE') # find power of machine
print(mbase)

Differentiate entries in Block Data with a flag in Fortran77

I am initializing a header struct in Fortran 77 in a BLOCK DATA . Whereas I have two versions of this *.f - file. One got an update with new functionality but the old version should be still supported.
The new version looks alike:
Block Data INIT_HS
Implicit None
C
Include 'hdr_str.inc'
C
Data (HDR_STRUC (I, NAVA), I = 1, 5)/
& CITY , AREA,
& LAT , LONG,
& ELEV,
& END/
C
Data (HDR_STRUC (I, NAVB), I = 1, 3)/
& CITY , CUST AREA,
& NAME , END/
C
Data HDR_STRING (CODE) /'CODE'/
Data HDR_STRING (ALT ) /'ALT'/
Data HDR_STRING (LAT) /'LAT'/
Data HDR_STRING (LON) /'LON'/
Data HDR_STRING (ACCL) /'ACCL'/
END
And in the old version some entries are not there:
Block Data INIT_HS
Implicit None
C
Include 'hdr_str.inc'
C
Data (HDR_STRUC (I, NAVA), I = 1, 3)/
& LAT , LONG,
& ELEV,
& END/
C
Data (HDR_STRUC (I, NAVB), I = 1, 2)/
& CITY , CUST AREA,
& END/
C
Data HDR_STRING (CODE) /'CODE'/
Data HDR_STRING (LAT) /'LAT'/
Data HDR_STRING (LON) /'LON'/
END
For the rest of the merged source code, I found a solution in handing over an argument when calling the executable:
DUMMY.exe VERSOLD
or:
DUMMY.exe VERSNEW
So I implemented a function setting a flag which version it is. For normal PROGRAM, SUBROUTINE etc. it is no issue but within this BLOCK DATA I can not just implement a CALL GETVERS ... IF (VERSOLD) THEN
I will get the following Error message from the compiler (gfortran -m32 -std=legacy -ffixed-line-length-none -c -g -fno-automatic -fno-second-underscore -finit-local-zero ) (..yes former g77..)
Error: Syntax error in DATA statement at (1)
Of course I could just implement a second BLOCK DATA with a different name.
I really wonder whether there is any other nice solution for this?

How to get optimality gap using CPLEX Python API?

How can the optimality gap (relative and absolute) be obtained using CPLEX Python API (CPLEX 12.5, Python 2.7.15)? Is there any function such as get_optimal_gap() that would give the optimality gap? Or is parsing the output (as mentioned here) the only way? I see that there are custom functions such as solution.get_objective_value() - it would be nice if someone can suggest online resources that have a list of all functions that can be applied on the cplex object/file. Currently I am using the following code (courtesy: this IBM document):
import cplex
import sys
def sample1(filename):
c = cplex.Cplex(filename)
try:
c.solve()
except CplexSolverError:
print "Exception raised during solve"
return
# solution.get_status() returns an integer code
status = c.solution.get_status()
print "Solution status = " , status, ":",
print c.solution.status[status]
print "Objective value = " , c.solution.get_objective_value()
sample1(filename)
The documentation for the CPLEX Python API is here (currently version 12.8).
To get the relative mip gap, you can use c.solution.MIP.get_mip_relative_gap(). To calculate the absolute mip gap you'll need c.solution.MIP.get_best_objective().
If you haven't already, you'll also want to take a look at the CPX_PARAM_EPGAP and CPX_PARAM_EPAGAP parameters.

Python: Writing input data as it is to output file

So, i'm a total noob when it comes to programming, especially python. I'm trying to merge two files(based on my requirements) and store the result into an output file. I am easily being able to do the merge, but the issue i'm facing is with the data format. You see, the data in the output file must be in the same format as the input file
These are my input files:
File1:
ID,CLASS,BOARD_ID
3620694,Smart,233049933699
3620724,Smart,233200309044
3620819,Smart,233200971094
3620831,Smart,233201075614
3620865,Smart,233201516374
3620870,Smart,233201553354
3620906,Smart,233201863244
3620929,Smart,233201972254
3620963,Smart,233202244014
3621008,Smart,233202600234
3621107,Smart,233203534474
3621158,Smart,233204019454
3621179,Smart,233204093854
3621252,Smart,233204801364
3621254,Smart,233204815324
3621266,Smart,233205000144
3621275,Smart,233205104774
3621288,Smart,233205182584
File2:
CDUS,CBSCS,CTRS,CTRS_ID
0,0,0.000000000375,233010056572
0,0,4.0746,233200309044
0,0,0.6182,233200971094
0,0,15.4834,233201075614
0,0,2.2459,233201516374
0,0,0.148,233201553354
0,0,0.0468,233201863244
0,0,0.5045,233201972254
0,0,0.0000000000485,233049933699
So this is my python script:
import pandas
#pandas.set_option('display.precision',13)
csv1 = pandas.read_csv('OUTPUT_1707000867_BundleCrossCellData_45432477_0_0.txt',dtype={'BOARD_ID': str})
csv2 = pandas.read_csv('I2.txt',dtype={'CTRS_ID': str}).rename(columns={'CTRS_ID':'BOARD_ID'})
merged = pandas.merge(csv1, csv2,left_on=['BOARD_ID'],right_on=['BOARD_ID'],how='left',suffixes=('#x', '#y'), sort=True)
merged.to_csv("Op2.txt", index=False,date_format='%Y/%m/%d %H:%M:%S.000',float_format='%.13f')
Output received upon execution:
Op.txt
ID,CLASS,BOARD_ID,CDUS,CBSCS,CTRS
3620694,Smart,233049933699,0.0000000000000,0.0000000000000,0.0000000000485
3620724,Smart,233200309044,0.0000000000000,0.0000000000000,4.0746000000000
3620819,Smart,233200971094,0.0000000000000,0.0000000000000,0.6182000000000
3620831,Smart,233201075614,0.0000000000000,0.0000000000000,15.4834000000000
3620865,Smart,233201516374,0.0000000000000,0.0000000000000,2.2459000000000
3620870,Smart,233201553354,0.0000000000000,0.0000000000000,0.1480000000000
3620906,Smart,233201863244,0.0000000000000,0.0000000000000,0.0468000000000
3620929,Smart,233201972254,0.0000000000000,0.0000000000000,0.5045000000000
3620963,Smart,233202244014,,,
3621008,Smart,233202600234,,,
3621107,Smart,233203534474,,,
3621158,Smart,233204019454,,,
3621179,Smart,233204093854,,,
3621252,Smart,233204801364,,,
3621254,Smart,233204815324,,,
3621266,Smart,233205000144,,,
3621275,Smart,233205104774,,,
3621288,Smart,233205182584,,,
Expected Output:
ID,CLASS,BOARD_ID,CDUS,CBSCS,CTRS
3620694,Smart,233049933699,0,0,0.0000000000485
3620724,Smart,233200309044,0,0,4.0746000000000
3620819,Smart,233200971094,0,0,0.6182000000000
3620831,Smart,233201075614,0,0,15.4834000000000
3620865,Smart,233201516374,0,0,2.2459000000000
3620870,Smart,233201553354,0,0,0.1480000000000
3620906,Smart,233201863244,0,0,0.0468000000000
3620929,Smart,233201972254,0,0,0.5045000000000
3620963,Smart,233202244014,,,
3621008,Smart,233202600234,,,
3621107,Smart,233203534474,,,
3621158,Smart,233204019454,,,
3621179,Smart,233204093854,,,
3621252,Smart,233204801364,,,
3621254,Smart,233204815324,,,
3621266,Smart,233205000144,,,
3621275,Smart,233205104774,,,
3621288,Smart,233205182584,,,
As you can see in Op.txt, values of CDUS and CBSCS are not in the same format as in File2.txt. For obvious reasons both have to be in same format.
Is there a way to resolve this issue?
Also since the input files are being generated at runtime, i cannot statically type-cast a certain column to a certain type.
I also referenced following links, but didnt find an appropriate solution. Any help would be very much appreciated.
How do I suppress scientific notation in Python?
Force python to not output a float in standard form / scientific notation / exponential form
Casting float to string without scientific notation
supress scientific notation when writing python floats to files
Suppressing scientific notation in pandas?

converting pipe seperated raw data to xlsx using xlsxwriter module of python

I'm new to python and trying to write a small code to convert raw pipe seperated data to xlsx. Details as below :
raw data
a|b|c|d|
.
.
.
1000s of row
expected output
a b c d {each representing one cell in xlsx}
My code:
workbook=xlsxwriter.Workbook('ABC.xlsx')
worksheet=workbook.add_worksheet()
input_file=(raw_data.txt,'r')
row=0
col=0
for line in input_file:
line=line.split('|')
workseet.write(row,col,line)
row +=1
worsheet.close()
The output that i'm getting is :
a b c d (all in single cell)
Any pointers on what i'm missing here will be helpful.