SunPower / PVMismatch

An explicit Python PV system IV & PV curve trace calculator which can also calculate mismatch.
http://sunpower.github.io/PVMismatch/
BSD 3-Clause "New" or "Revised" License
79 stars 30 forks source link

Bypass diodes configurability #72

Closed chetan201 closed 6 years ago

chetan201 commented 6 years ago

New feature to let the user model various scenarios with bypass diodes configurations.

:param Vbypass: float|list of :float
    bypass diode trigger voltage [V]
    default case - one bypass diode per cell string (VBYPASS = -0.5V(V))
    float - one bypass diode per cell string with Vf = Vbypass (V)
    len(list) == 1 - one bypass diode per module (bypasses entire module )
    len(list) == len(cell_pos) - bypass diode value across cell string as 
                                 defined in the list

a code snippet to verify the various scenarios

import pvmismatch
from matplotlib import pyplot as plt
pvconstants = pvmismatch.pvmismatch_lib.pvconstants.PVconstants(npts=1001)

pvm = pvmismatch.pvmismatch_lib.pvmodule.PVmodule(Vbypass = [None, None, None])
plt.plot(pvm.Vmod, pvm.Imod, label ='No bypass diodes')

pvm = pvmismatch.pvmismatch_lib.pvmodule.PVmodule(Vbypass = [None, None,-0.5])
plt.plot(pvm.Vmod, pvm.Imod, label ='only one cell string has a bypass diode')

pvm = pvmismatch.pvmismatch_lib.pvmodule.PVmodule(Vbypass = [-0.5, None,-0.5])
plt.plot(pvm.Vmod, pvm.Imod, label ='two bypass diodes (middle removed)')

pvm = pvmismatch.pvmismatch_lib.pvmodule.PVmodule(Vbypass = -0.2)
plt.plot(pvm.Vmod, pvm.Imod, label ='all bypass diodes')

pvm = pvmismatch.pvmismatch_lib.pvmodule.PVmodule(Vbypass = [-0.5])
plt.plot(pvm.Vmod, pvm.Imod, label ='1 bypass diode across the module')

pvm = pvmismatch.pvmismatch_lib.pvmodule.PVmodule()
plt.plot(pvm.Vmod, pvm.Imod, label ='default')

plt.grid(True)
plt.xlabel('Voltage (V)')
plt.ylabel('Current (A)')

plt.legend()
chetan201 commented 6 years ago

@mikofski How do I update the documentation for PVMismatch? I think this new enhancement should be documented.

mikofski commented 6 years ago

I've added something to the wiki regarding documentation here.

mikofski commented 6 years ago

PS I would also ask @bmeyers to review this. He spent a lot of time optimizing it for speed with large arrays. The for loop in here may slow things down, so some benchmarking with very large arrays should double check that there's no impact on performance.

chetan201 commented 6 years ago

@mikofski Thanks for the detailed review! I would like to make the bypass diode feature more configurable and I think your recommendations will really help that goal. This will be a branch under construction for a bit longer I think.

As for using pytest, I am all for it!

chetan201 commented 6 years ago

Hi @mikofski @bmeyers , Would you guys mind taking a look through the PR? I think it is in a good shape at this point. I would like to start using it in the master. Thanks for your time and continued support with PVMismatch! Chetan.

image

Code snippet to recreate the figure -


from nose.tools import ok_
from pvmismatch.pvmismatch_lib.pvmodule import PVmodule, TCT492, PCT492
import numpy as np
from matplotlib import pyplot as plt

pvm_list = []

pvm = PVmodule(Vbypass = [None, None, None])
ok_(np.isclose(pvm.Vmod.min(), -530.6169665707829))
pvm_list.append(pvm)

# only one cell string has a bypass diode
pvm = PVmodule(Vbypass = [None, None,-0.5])
ok_(np.isclose(pvm.Vmod.min(), -398.46272492808714))
pvm_list.append(pvm)

# two bypass diodes (middle removed)
pvm = PVmodule(Vbypass = [-0.5, None,-0.5])
ok_(np.isclose(pvm.Vmod.min(), -266.30848328539145))
pvm_list.append(pvm)

# all bypass diodes - same values
pvm = PVmodule(Vbypass = -0.2)
ok_(np.isclose(pvm.Vmod.min(), -0.6))
pvm_list.append(pvm)

# one bypass diode across the module
pvm = PVmodule(Vbypass = [-0.7])
ok_(np.isclose(pvm.Vmod.min(), -0.7))
pvm_list.append(pvm)

# default case
pvm = PVmodule()
ok_(np.isclose(pvm.Vmod.min(), pvm.Vbypass * 3))

plt.figure()
for pvm in pvm_list:
    plt.plot(pvm.Vmod, pvm.Imod)
plt.grid()
plt.legend(['No diodes', 'One diode two missing', 'two diodes, center missing', 'all diodes','module bypass'])
plt.show()
plt.xlabel('Voltage')
plt.ylabel('Current')```
chetan201 commented 6 years ago

@amir-asgharzadeh Thanks for the review. I made the change and now merging.