有Bokeh回调更新列表而不是一个ColumnDataSource? [英] Have Bokeh Callback update a list instead of a ColumnDataSource?

查看:642
本文介绍了有Bokeh回调更新列表而不是一个ColumnDataSource?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我的问题与修改



我有一个矩阵m或原始数据,其中每一行对应一对变换的x,y坐标空间(参见#MockData代码部分)。



x,y坐标绘制在左图。我试图更改示例,以便当我在左图中选择一些点,右图将显示相应行的线图。



我已经将问题缩小到了正确的位置,显示了indices列表中指定的所需数据。但是,我不能找出如何链接回调函数到索引列表。 (








b $ b

  from bokeh.plotting import figure,output_file,show,ColumnDataSource,hplot 
from bokeh.models import HoverTool,Callback,ColumnDataSource
import pandas as pd
output_file(Map.html)

#模拟数据
m = np.zeros((6,11))
for i in range :
for(11)中的j:
m [i,j] = i + j
x = [0,1,2,3,4,5] y = [0,2,4,6,8,10]
m0 = m.transpose()
m1 = pd.DataFrame(m0,index = ['0','1' (0,len(m),...,len(m))中, 1).astype(str)])

#First plot
s1 = ColumnDataSource(data = dict(x = x,y = y))
p1 = = [lasso_select],plot_width = 600,plot_height = 400)
p1.scatter('x','y',fill_color ='black',line_color = None,size = 10,source = s1)

#Second plot
s2 = ColumnDataSource(data = dict(z = [])
p2 = figure(plot_width = 400,plot_height = 400)
m1 = ColumnDataSource(m1)
indices = [1,3,4]
for i in indices:
p2.line(np.arange(0,11,1),'%s'% i,source = m1)

s1.callback = Callback(args = dict(s2 = s2),code =
var inds = cb_obj.get '1d'] .index;
var d2 = s2.get('data');
d2 ['z'] = []
for(i = 0; i d2 ['z']。push(inds [i])}
s2.trigger('change');


layout = hplot(p1,p2)
show(layout)



问题:



使用Bokeh文档中的示例。我试图从左边窗口中的选择获取索引,并使用它们从原始数据的矩阵获取适当的行,并绘制行。
详细信息:

\\ b $ b我从一个矩阵开始,每个列是一年,每一行是一个位置。我在矩阵上运行sklearn频谱嵌入以表征数据并获得矩阵,其中每个列以某种方式描述数据。我将前3列绘制为x,y坐标和颜色。
接下来我试图修改示例,使得当我选择一些点时,第二个图形将其原始数据(行)显示为单独的行。

解决方案

没有任何回应,也没有在这里和散景邮件列表,让我相信这是不可能使用回调以这种方式,所以我不得不解决它,并接受当前的限制,这是无法使回调大小动态。



为了数据探索的目的,这将无论如何。

  from bokeh.plotting import figure,output_file,显示,ColumnDataSource,hplot 
from bokeh.models import HoverTool,Callback,ColumnDataSource
import pandas as pd
output_file(bla.html)

#模拟数据范围(2,6)中的i的
m:范围(11)中的j的

m [i,j] = i + j
x = [0,1,2,3,4,5]; y = [0,2,4,6,8,10]
m0 = m.transpose()
m1 = pd.DataFrame(m0,index = ['0','1' (0,len(m),...,len(m))中, 1).astype(str)])

#First plot
s1 = ColumnDataSource(data = dict(x = x,y = y))
p1 = = [lasso_select],plot_width = 600,plot_height = 400)
p1.scatter('x','y',fill_color ='black',line_color = None,size = 10,source = s1)

#Second plot
s2 = ColumnDataSource(data = dict(x = [],y = [],y2 = []))
p2 = figure(plot_width = plot_height = 400,tools = [])

m1 = ColumnDataSource(m1)#Actual第二个绘图的数据源
p2.line(np.arange(0,100,1),'y' ,source = s2)#从原始数据 - 系列1
p2.line(np.arange(0,100,1),'y2',source = s2)#从原始数据 - 系列2

s1.callback = Callback(args = dict(s2 = s2,m1 = m1),code =
var inds = cb_obj.get('selected')['1d']。 b $ b var d1 = m1.get('data');
var d2 = s2.get('data');
d2 ['y'] = []
d2 [ 'y2'] = []
for(i = 0; i< 11; push(d1 [inds ['0']] [i]),
d2 ['y2']。 ]] [i])
}
s2.trigger('change');


layout = hplot(p1,p2)
show(layout)

代码现在绘制所选数据中前两个索引的原始数据,限制是必须预定义原始数据系列的数量,因此代码只会另外它还需要至少两行来执行,它不会只为一个点选择的工作,因此,如果我预定义更多的线被绘制,我将总是选择该点数。


My question has to do with modifying this example from the Bokeh Gallery.

I have a matrix m or raw data, in which every row corresponds to a pair of x,y coordinates in a transformed space (see #MockData part of code).

The x,y coordinates are plotted on the left plot. I am trying to change the example so that, when I select some points in the left figure, the right figure will display line plots of the corresponding rows.

I've narrowed the problem down to the point, where the right figure will show the desired data as specified by the "indices" list. I cannot, however, figure out how to link the Callback function to the indices list. (Currently the Callback uselessly updates source s2 with the indices.)

Code should work when copied:

from bokeh.plotting import figure, output_file, show, ColumnDataSource, hplot
from bokeh.models import HoverTool, Callback, ColumnDataSource
import pandas as pd
output_file("Map.html")

# Mock data
m = np.zeros((6,11))
for i in range(6):
    for j in range(11):
        m[i,j] = i+j
x = [0,1,2,3,4,5]; y = [0,2,4,6,8,10]
m0 = m.transpose()
m1 = pd.DataFrame(m0, index=['0','1','2','3','4','5','6','7','8','9','10'], columns=[np.arange(0,len(m),1).astype(str)])

#First plot
s1 = ColumnDataSource(data=dict(x=x,y=y))
p1 = figure(tools=["lasso_select"], plot_width=600, plot_height=400)
p1.scatter('x', 'y', fill_color='black', line_color=None, size=10, source=s1)

#Second plot
s2 = ColumnDataSource(data=dict(z=[]))
p2 = figure(plot_width=400, plot_height=400)    
m1 = ColumnDataSource(m1)
indices = [1,3,4]
for i in indices:
    p2.line(np.arange(0,11,1), '%s'%i ,  source=m1)

s1.callback = Callback(args=dict(s2=s2), code="""
  var inds = cb_obj.get('selected')['1d'].indices;
  var d2 = s2.get('data');
  d2['z'] = []
  for (i = 0; i < inds.length; i++) {
      d2['z'].push(inds[i])}
  s2.trigger('change'); 
""")

layout = hplot(p1, p2)
show(layout)

Original question:

Working with the example in Bokeh documentation. I am trying to get indices from the selection in the left window and use them to get appropriate row from a matrix with original data and plot the row. In detail:

I start with a matrix of values, where each column is a year and each row a location. I run a sklearn Spectral Embedding on the matrix to characterize the data and get a matrix, where each column somehow describes the data. I plot the first 3 columns as x,y coordinates and a color. Next I am trying to modify the example such that, when I select some points, the second graph displays their original data (rows) as separate lines. The relevant code mostly taken from the example is below.

解决方案

Not having any responses neither here nor in Bokeh mailing list, leads me to believe it's impossible to use callback in this manner, so I had to work around it and accept the current limitation, which is the inability to make the callback "size" dynamic.

For the purpose of data exploration this will do anyway.

from bokeh.plotting import figure, output_file, show, ColumnDataSource, hplot
from bokeh.models import HoverTool, Callback, ColumnDataSource
import pandas as pd
output_file("bla.html")

# Mock data
m = np.ones((6,11))
for i in range(2,6):
    for j in range(11):
        m[i,j] = i+j
x = [0,1,2,3,4,5]; y = [0,2,4,6,8,10]
m0 = m.transpose()
m1 = pd.DataFrame(m0, index=['0','1','2','3','4','5','6','7','8','9','10'], columns=[np.arange(0,len(m),1).astype(str)])

#First plot
s1 = ColumnDataSource(data=dict(x=x,y=y))
p1 = figure(tools=["lasso_select"], plot_width=600, plot_height=400)
p1.scatter('x', 'y', fill_color='black', line_color=None, size=10, source=s1)

#Second plot
s2 = ColumnDataSource(data=dict(x=[],y=[],y2=[]))
p2 = figure(plot_width=400, plot_height=400, tools =[])

m1 = ColumnDataSource(m1) #Actual Datasource for the second plot
p2.line(np.arange(0,100,1), 'y' , source=s2) # From original data - series 1
p2.line(np.arange(0,100,1), 'y2' , source=s2) # From original data - series 2

s1.callback = Callback(args=dict(s2=s2, m1=m1), code="""
  var inds = cb_obj.get('selected')['1d'].indices;
  var d1 = m1.get('data'); 
  var d2 = s2.get('data');
  d2['y'] = []
  d2['y2'] = []
  for (i = 0; i < 11; i++) {
    d2['y'].push(d1[inds['0']][i]),
    d2['y2'].push(d1[inds['1']][i])
  }
  s2.trigger('change'); 
""")

layout = hplot(p1, p2)
show(layout)

The code now plots the original data for the first two indices in the selected data. The limitation is that the number of series of original data has to be predefined, so the code will only ever plot two lines. Furthermore it also needs at least two lines to execute. It won't work for only one point selected. Therefore if I predefine more lines to be graphed I will always have to select that number of points.

这篇关于有Bokeh回调更新列表而不是一个ColumnDataSource?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆