Writing a for loop with an IntegerField rather than an int - django

I'm trying to create a for loop for creating a dynamic number of objects in Otree, which extends Django (I know, crazy idea, but bear with me). Unfortunately the latest version of otree will throw compile time errors if you attempt to use integers in your code. So for example, the following code:
num_decs = 8
for d in range(1, num_decs + 1):
locals()['dec_r'+str(r)+'_'+str(d)]= models.CharField(choices=[Constants.choice1_name, Constants.choice2_name],widget=widgets.RadioSelectHorizontal(),blank=False,initial='blank')
Will throw the following error (as opposed to a warning, which occurred with previous versions of Otree):
(otree.E111) NonModelFieldAttr: Player has attribute "d", which is not a model field, and will therefore not be saved to the database.
I imagine that the best way to resolve this would be to declare d in the for loop as an IntegerField object and then cast it as an int using the int() method as follows:
num_decs = models.IntegerField(initial=8)
d = models.IntegerField(default=0)
for d in range(1, num_decs.__int__() + 1):
But I receive an error that IntegerField lacks a int() method. What should I do to cast an IntegerField as an int for a for loop? Thanks!

For those of you who are out and about using Otree, I have a solution!
Add the following code to the end of your for loop:
del d
del num_decs
And you shouldn't have any problems :)

Related

How to use a mutable Param pyomo?

I'm trying to make Param mutable with initializer zero but when I tried to read the Param in the constraint its doesn't understand what is reading, the only way that I found to read is using .value but when the problem finishes declaring the whole constraint. the solver found the first solution but when I defined the new param value, it doesn't change the value of the param. I know if I am doing bad the declared or I haven't found the correct white to do that.
As a solver im using CPLEX
This is the way i defined the Param:
model.s_value = pe.Param(mutable=True, initialize=0)
But if I use the Param as a normal Param is a constraint promo sent this message:
ValueError: Constraint 'def_constraint[0]' encountered a strict inequality expression ('>' or '<'). All constraints must be formulated using using '<=', '>=', or '=='.
I think is because when pyomo tired to read the param that sends an object like this:
pyomo.core.base.param.IndexedParam object at 0x1939C6A0
After declaring all the variable I put the solver inside a for and there I redefine the value of the Param:
model.s_value.value= new_value
Please. Someone can explain to me who can I use correctly the mutable Param and how can I iterate the model.
This is a simple example of changing the value of a mutable parameter. You didn't post a full set of executable code above, so it is difficult to figure out what is going on. If this below doesn't answer your question, request you update (edit) your post above with a minimal reproducible example.
import pyomo.environ as pyo
m = pyo.ConcreteModel()
m.x = pyo.Var(domain=pyo.NonNegativeReals)
m.p = pyo.Param(mutable=True, initialize = 10)
# the problem
m.OBJ = pyo.Objective(expr=m.x)
m.c1 = pyo.Constraint(expr=m.x >= m.p)
solver = pyo.SolverFactory('glpk')
# solve it...
results = solver.solve(m)
m.display() # x=10
# change the mutable parameter
m.p = 5
# re-solve it
results = solver.solve(m)
m.display() # x=5

Filter objects or (if 0 found) get all objects in Django with one DB hit

Is there a way in Django to achieve the following in one DB hit (Debug Toolbar shows 2 queries)?
q = SomeModel.objects.filter(name=name).order_by(some_field)
if q.count() == 0:
q = SomeModel.objects.all().order_by(some_field)
I want to check if there are objects with a given name. If yes, then return them. If not, return all objects. All done in one query.
I've checked Subquery, Q, conditional expressions but still don't see how to fit it into one query.
Ok, much as I resisted (I still think it's premature optimization), curiosity got the better of me. This is not pretty but does the trick:
from django.db.models import Q, Exists
name_qset = SomeObject.objects.filter(name=name)
q_func = Q(name_exists=True, name=name) | Q(name_exists=False)
q = SomeModel.objects.annotate(
name_exists=Exists(name_qset)
).filter(q_func).order_by(some_field)
Tried it out and definitely only one query. Interesting to see if it is actually appreciably faster for large datasets...
You best bet is to use .exists(), otherwise your code is fine
q = SomeModel.objects.filter(name=name).order_by(some_field)
if not q.exists():
q = SomeModel.objects.all().order_by(some_field)

Trying to import dictionary to work with from a url; 'unicode' object not callable

I'm new to coding and have searched as best I can to find out how to solve this before asking.
I'm trying to pull information from poloniex.com REST api, which is in JSon format I believe. I can import the data, and work with it a little bit, but when I try to call and use the elements in the contained dictionaries, I get "'unicode' object not callable". How can I use this information? The end goal with this data is to pull the "BTC: "(volume)" for each coin pair and test if it is <100, and if not, append it to a new list.
The data is presented like this or you can see yourself at https://poloniex.com/public?command=return24hVolume:
{"BTC_LTC":{"BTC":"2.23248854","LTC":"87.10381314"},"BTC_NXT":{"BTC":"0.981616","NXT":"14145"}, ... "totalBTC":"81.89657704","totalLTC":"78.52083806"}
And my code I've been trying to get to work with currently looks like this(I've tried to iterate the information I want a million different ways, so I dunno what example to give for that part, but this is how I am importing the data):
returnvolume = urllib2.urlopen(urllib2.Request('https://poloniex.com/public?command=return24hVolume'))
coinvolume = json.loads(returnvolume.read())
coinvolume = dict(coinvolume)
No matter how I try to use the data I've pulled, I get an error stating:
"unicode' object not callable."
I'd really appreciate a little help, I'm concerned I may be approaching this the wrong way as I haven't been able to get anything to work, or maybe I'm just missing something rudimentary, I'm not sure.
Thank you very much for your time!
Thanks to another user, downshift, I have discovered the answer!
d = {}
for k, v in coinvolume.items():
try:
if float(v['BTC']) > 100:
d[k] = v
except KeyError:
d[k] = v
except TypeError:
if v > 100:
d[k] = k
This creates a new list, d, and adds every coin with a 'BTC' volume > 100 to this new list.
Thanks again downshift, and I hope this helps others as well!

in_round() function in oTree

Consider a game with 3 rounds. In every round the player makes a choice (stored in the variable choice).
Now, in the 3rd round I want to call someFunction and thereby access the choice made in the 2nd round.
Unfortunately someFunction returns None. I do not understand why. If I place the function call in a template file, everything works out fine.
Help would be appriciated - I ve been searching for hours.
class Subsession(BaseSubsession):
def before_session_starts(self):
if self.round_number == 3:
for player in self.get_players():
player.participant.vars['someKey'] = player.someFunction()
class Player(BasePlayer):
choice = models.CharField(initial=None,
choices=['A','B','C'],
widget=widgets.RadioSelect())
def someFunction(self):
return self.in_round(2).choice
Why is this happening?
the before_session_starts function is executed before the session starts (hence its name). Thus, when it is executed the player has not done his/her choice yet. That is why someFunction returns None.
You can set player.participant.vars['someKey'] = self.player.choice in the end of 2nd round, which will give you result you are looking for.
class Choice(Page):
def before_next_page(self):
if self.player.round_number == 2:
player.participant.vars['someKey'] = self.player.choice

Joining many callisto images

c1 = CallistoSpectrogram.read('BIR_20110922_101500_01.fit')
c2 = CallistoSpectrogram.read('BIR_20110922_103000_01.fit')
d = CallistoSpectrogram.join_many([c1, c2])
If I want to join approximately 40 files like this, it is throwing the following error
ValueError: Too large gap.
Is there any limit in number?
This error is an internal error of the sunpy package that you are using. Really your question is not to do with python but to do with that package. You need to tag it with that.
But we can see what's going on by looking at the source, eg here. It shows that the ValueError is thrown when two adjacent spectra are separated by more than the maxgap parameter which defaults to zero.
So one fix might be simply to pass in maxgap = None
d = CallistoSpectrogram.join_many([c1, c2],maxgap = None)
That assumes you don't mind the gaps, of course.