问题
I was following the example on how to handle multiple dependent widgets on jupyter notebooks from here:
Dynamically changing dropdowns in IPython notebook widgets and Spyre
In that example the code solution was the following:
from IPython.html import widgets
from IPython.display import display
geo={'USA':['CHI','NYC'],'Russia':['MOW','LED']}
def print_city(city):
print city
def select_city(country):
cityW.options = geo[country]
scW = widgets.Dropdown(options=geo.keys())
init = scW.value
cityW = widgets.Dropdown(options=geo[init])
j = widgets.interactive(print_city, city=cityW)
i = widgets.interactive(select_city, country=scW)
display(i)
display(j)
so, the second dropdown is dependent on the value of the first one. Here the question: What if i want to create a third dropdown that is dependent on the value of the second one? Let's say that each of the cities above (CHI, NYC, MOW, LED) have some districts, and I'd like a third dropdown that change every time that a city is updated.
Hope that the problem is clear, thank you!
回答1:
Just in case you never found a solution: I have one here that works in python 3. I've commented everything that I changed from the original code. I hope it helps!
from IPython.html import widgets
from IPython.display import display
geo={'USA':['CHI','NYC'],'Russia':['MOW','LED']}
geo2={'CHI':['1','2'],'NYC':['3','4'],'MOW':['5','6'],'LED':['7','8']} #create dictionary with city districts
def print_city(city,district):
print(city)
print(district) #add in command to print district
def select_city(country):
cityW.options = geo[country]
#add in 'select district' function that looks in the new dictionary
def select_district(city):
districtW.options = geo2[city]
scW = widgets.Dropdown(options=geo.keys())
init = scW.value
cityW = widgets.Dropdown(options=geo[init])
init2= cityW.value #new start value for district dropdown
districtW = widgets.Dropdown(options=geo2[init2]) #define district dropdown widget
j = widgets.interactive(print_city, city=cityW, district=districtW) #define district value
i = widgets.interactive(select_city, country=scW)
k = widgets.interactive(select_district, city=cityW) #call everything together with new interactive
display(i)
display(j)
回答2:
Using interactive
is somewhat clumsy for me. I have provided an answer clearer and conciser for two dependent widgets in the original page here. Below I provide my answer for multiple dependent widgets.
from ipywidgets import interact, Dropdown
geo = {'USA':['CHI','NYC'],'Russia':['MOW','LED']}
geo2={'CHI':['1','2'],'NYC':['3','4'],'MOW':['5','6'],'LED':['7','8']}
countryW = Dropdown(options = geo.keys())
cityW = Dropdown(options = geo[countryW.value]) # options = geo[countryW.value] is to remove inital error but not that necessary.
districtW = Dropdown()
@interact(country = countryW, city = cityW, district = districtW)
def print_city(country, city, district):
cityW.options = geo[country] # Here is the trick, i.e. update cityW.options based on country, namely countryW.value.
districtW.options = geo2[city] # Dittoo
print(country, city, district)
An alternative would be to use explicit update functions shown as follows. Bear in mind that the update speed may not be that quick. The code works well.
from ipywidgets import interact, Dropdown
geo = {'USA':['CHI','NYC'],'Russia':['MOW','LED']}
geo2={'CHI':['1','2'],'NYC':['3','4'],'MOW':['5','6'],'LED':['7','8']}
countryW = Dropdown(options = geo.keys())
cityW = Dropdown()
districtW = Dropdown()
def update_cityW_options(*args): # *args represent zero (case here) or more arguments.
cityW.options = geo[countryW.value]
cityW.observe(update_cityW_options) # Here is the trick, i.e. update cityW.options based on countryW.value.
def update_districtW_options(*args):
districtW.options = geo2[cityW.value]
districtW.observe(update_districtW_options)
@interact(country = countryW, city = cityW, district = districtW)
def print_city(country, city, district):
print(country, city, district)
来源:https://stackoverflow.com/questions/48407059/multiple-dependent-widgets-dropdown-menu-on-jupyter-notebook