Ask Your Question
0

Is there way to identify all radial lines through PSS\E+Python?

asked 2014-08-13 16:49:35 -0500

ypwang gravatar image

Hello everyone,

I wanted identify all radial lines before creating a list of N-1 branch contingencies. But it is kind of meaningless to create a radial-line contingency especially if that radial line is connected to some loaded bus. So I wonder if there are python modules that can help me do this automatically. So far, I haven't found any modules can do this for me. In a naive way, I can I can use some python module to read the .raw data for branch data's "from/to bus" information and filter those buses that only appear once in from- and to- list and the branch to which it connects should be those radial lines. I know in this way, we will miss some special radial lines that even is connected to two buses, but losing which still will result in an island.

Could anyone advise on this issue.

Really appreciate your kind help and time.

Yp

edit retag flag offensive close merge delete

3 answers

Sort by ยป oldest newest most voted
1

answered 2014-08-18 02:46:56 -0500

rimux gravatar image

updated 2014-08-21 23:41:26 -0500

I would suggest to go through a list of branches and disconnect them one by one. After disconnection of the branch, check if there are no islands - if you will get an island this means that branch is radial. e.g.:

import psspy

branches=[[101,102,'1'], [201,202,'1']]

psspy.progress_output(6,"",[0,0])

List=[]
for b in branches:
  ierr, status = psspy.brnint(b[0], b[1], b[2], "STATUS")
  if ierr==0 and status==1: #branch is on
    ierr = psspy.branch_chng(b[0], b[1], b[2], 
               [0,_i,_i,_i,_i,_i], [_f,_f,_f,_f,_f,_f,_f,_f,_f,_f,_f,_f,_f,_f,_f])   
    if ierr==0:
      ierr, n = psspy.tree(1,0)
      if ierr==0 and n>0: #island detected
        # b is radial branch...
        print 'branch',b[0], b[1], b[2],'is radial'
        ierr, n = psspy.tree(2,-1)
      else:
        #branch is not radial 
        print 'branch',b[0], b[1], b[2],'is not radial'
        List.append(b)              
      ierr = psspy.branch_chng(b[0], b[1], b[2],
                 [1,_i,_i,_i,_i,_i],[_f,_f,_f,_f,_f,_f,_f,_f,_f,_f,_f,_f,_f,_f,_f])  
#List will contain only non-radial branches (and only with status=on)

psspy.progress_output(1,"",[0,0])
print 'Non-radial branches:',List
edit flag offensive delete link more

Comments

I like your solution, which should work much better than what I wrote yesterday ( I will post my code as another answer (not good as yours:-)) below. My code can only identify those radial lines one of whose bus is only connected to this particular branch. Can I ask how do you define an island?

ypwang gravatar imageypwang ( 2014-08-18 11:05:16 -0500 )edit

Island means - there are bus or buses which do not have connection to any type 3 bus (swingbus).

rimux gravatar imagerimux ( 2014-08-18 12:23:43 -0500 )edit

Also I am not sure you really need to filter those radial lines as psse DFAX command will automatically (I think so, will check this tomorrow) remove those contingencies that leads to formatting islands in the system.

rimux gravatar imagerimux ( 2014-08-18 12:34:46 -0500 )edit

That would be nice that DFAX can do this automatically. But based on my observation for "savnw" example, where I used the following code to find radial lines list and used "SINGLE BRANCH IN SUBSYSTEM 'savnw' ". It turned out one radial line(101-151) actually got processed in the ACCC.

ypwang gravatar imageypwang ( 2014-08-18 13:32:33 -0500 )edit

Seems that you are right, contingency list contains even those branches disconnection of which leads to island.

rimux gravatar imagerimux ( 2014-08-19 02:13:29 -0500 )edit
1

answered 2014-08-18 20:53:58 -0500

jconto gravatar image

updated 2017-12-07 20:52:15 -0500

The following algorithm may work:

loop0:

For every busx in the subsystem of interest:

if bus is type 2, continue #skip generator bus
count the number of buses it is connected to      #<- this is a loop
only if busx is connected to one bus, add to list those branches containing busx, then extrude such busx.
increase +1 single_bus counter

go back to loop0 until there is no more busx connected to one bus (single_bus counter=0).

8/24: I re-wrote rimux's code since it did not work in v.32. I posted the code at my googledrive site (https://drive.google.com/drive/folder...) filename = brnradial.py. This version does not bypass radial generators, connected to the grid with a transformer.

edit flag offensive delete link more

Comments

Good point that we should skip generator bus. I guess the rest of the algorithm will still count on the branch data information (i.e. fromBusId and toBusId).

ypwang gravatar imageypwang ( 2014-08-18 21:01:47 -0500 )edit

@jconto, Can you share the code that you re-wrote for V32. The link you provided is not working.

Ryangai gravatar imageRyangai ( 2017-12-06 09:43:36 -0500 )edit

I posted the code at my googledrive site (https://drive.google.com/drive/folders/0B7uS9L2Woq_7YzYzcGhXT2VQYXc) filename = brnradial.py Open PSSe, load a case and then run this code to get a list of radial branches.

jconto gravatar imagejconto ( 2017-12-07 20:47:39 -0500 )edit
0

answered 2014-08-18 11:05:56 -0500

ypwang gravatar image

updated 2014-08-21 21:57:42 -0500

# A function to find radial line one of whose bus is only connected this particular branch (consider both non-transformer branches and two-winding transformers)
def findRadialLines(psspy, subSysId):
    from collections import Counter

    # Find all bus numbers in a given subsystem
    allBusArr = psspy.abusint(subSysId, 2, 'NUMBER')

    # Consider all the internal branches (NO subsystem tie branches) and all non-transformer branches and two-winding transformers    
    ierr, (fromBusIdArr,) = psspy.abrnint(subSysId, 1, 1, 4, 1, 'FROMNUMBER')
    ierr, (toBusIdArr,) = psspy.abrnint(subSysId, 1, 1, 4, 1,  'TONUMBER')
    #ierr, (cktArr, ) = psspy.abrnchar(subSysId, 1, 1, 4, 1, 'ID')  # Can ignore this because if it is a radial line, then it for sure doesn't have a branch in parallel with it, i.e its CKT is always equal to 1

    # For each bus number, check if that bus number appears in either a 'fromBus' or 'toBus' list of all the branches in the subsystem    
    # first merge two lists to a big list
    fromtoBusList = fromBusIdArr + toBusIdArr
    print fromtoBusList

    # define a new list to hold all those buses that only appears in this big list
    radialLineBusList = []

    for busId, count in Counter(fromtoBusList).most_common():
        if count == 1:
            radialLineBusList.append(busId)

    # now depending on radialLineBusList, find thos radial lines
    # for each radialLineConnectedBus, find the branch sorting index (a reference to a fromBusID for a radial line) in the fromBusIdArr first
    branchDataIndx_radial = []

    for i in range(len(radialLineBusList)):
        if (radialLineBusList[i] in fromBusIdArr):
            branchDataIndx_radial.append(fromBusIdArr.index(radialLineBusList[i]))

        if (radialLineBusList[i] in toBusIdArr):
            branchDataIndx_radial.append(toBusIdArr.index(radialLineBusList[i]))


    # Now save all the radial lines to two separate lists: one for fromBusId and the other for toBusId
    fromBusId_radialLine = []
    toBusId_radialLine = []
    for i in range(len(branchDataIndx_radial)):
        # keep in mind that fromBusIdArr and toBusIdArr are sorted in the same order
        fromBusId_radialLine.append(fromBusIdArr[branchDataIndx_radial[i]])
        toBusId_radialLine.append(toBusIdArr[branchDataIndx_radial[i]])


    return  fromBusId_radialLine, toBusId_radialLine
edit flag offensive delete link more

Your Answer

Please start posting anonymously - your entry will be published after you log in or create a new account.

Add Answer

[hide preview]

Question Tools

1 follower

Stats

Asked: 2014-08-13 16:49:35 -0500

Seen: 2,730 times

Last updated: Dec 07 '17