JavaScript数据网格为数百万行
我需要使用JavaScript在网格中向用户呈现大量的数据行(即数百万行)。
用户不应该每次看到页面或仅查看有限数量的数据。
相反,它应该显示所有的数据都可用。
不是一次下载数据,而是随着用户来到他们(即通过滚动网格)下载小块。
行将不会被编辑通过这个前端,所以只读网格是可以接受的。
这种无缝寻呼存在哪些用JavaScript编写的数据网格?
( 免责声明:我是SlickGrid的作者 )
更新这现在已经在SlickGrid中实现。
请参阅http://github.com/mleibman/SlickGrid/issues#issue/22,了解有关使SlickGrid能够处理大量行的正在进行的讨论。;
问题是SlickGrid没有虚拟化滚动条本身 – 滚动区域的高度被设置为所有行的总高度。 当用户滚动时,行仍然被添加和删除,但滚动本身是由浏览器完成的。 这使得它非常快速而平稳(onscroll事件是非常缓慢的)。 需要注意的是浏览器的CSS引擎中存在一些限制元素潜在高度的错误/限制。 对于IE,恰好是0x123456或1193046像素。 对于其他浏览器则更高。
在“bignum-fix”分支中有一个实验性的解决方法,通过将“页面”设置为1M像素高度,然后使用这些页面内的相对位置填充可滚动区域,显着地提高了限制。 由于CSS引擎的高度限制似乎不同于实际的布局引擎,并且显着低于实际的布局引擎,所以这给我们提供了更高的上限。
我仍然在寻找一种方法来获取无限数量的行,而不会放弃SlickGrid目前在其他实现中所具有的性能优势。
鲁迪格,你能详细说明你是如何解决这个问题的吗?
http://wiki.github.com/mleibman/SlickGrid/
“ SlickGrid利用虚拟渲染,使您能够轻松处理数十万个项目,而不会降低性能。事实上,使用10行和100000行的网格在性能上没有区别。
一些亮点:
- 自适应虚拟滚动(处理成千上万行)
- 渲染速度非常快
- 为更丰富的单元格渲染的背景
- 可configuration和可定制
- 全键盘导航
- 调整列大小/重新sorting/显示/隐藏
- 色谱柱自动调整和强制配合
- 可插入单元格格式器和编辑器
- 支持编辑和创build新行。 “由mleibman
它是免费的(MIT许可证)。 它使用jQuery。
我认为最好的网格如下:
- Flexigrid: http ://flexigrid.info/
- jQuery网格: http : //www.trirand.com/blog/
- jqGridView: http ://plugins.jquery.com/project/jqGridView
- jqxGrid: http ://www.jqwidgets.com/
- Ingrid: http : //reconstrukt.com/ingrid/
- SlickGrid http://github.com/mleibman/SlickGrid
- 数据表 http://www.datatables.net/index
- ShieldUI http://demos.shieldui.com/web/grid-virtualization/performance-1mil-rows
我最好的3个选项是jqGrid,jqxGrid和DataTables。 他们可以使用数千行并支持虚拟化。
我并不是说要开始一场火焰战争,但是假设你的研究人员是人类的,你不像你想象的那么了解他们。 仅仅因为他们拥有数 PB的数据,并不能以任何有意义的方式查看甚至数百万条logging。 他们可能会说,他们希望看到数百万条logging,但这真是愚蠢。 让你最聪明的研究人员做一些基本的math:假设他们花费1秒查看每条logging。 以这样的速度,这将需要1000000秒,超过六个星期(40小时的工作周,没有rest的食物或盥洗室)。
他们(或者你)是否认真地认为一个人(看网格的人)能够集中注意力? 他们真的在1秒内完成了很多工作,或者他们(更有可能)过滤掉了不想要的东西? 我怀疑,在查看“合理大小”的子集后,他们可以向您描述一个filter,以便自动过滤这些logging。
正如paxdiablo,Sleeper Smith和Lasse V Karlsen所暗示的那样,你(他们)还没有想过要求。 另一方面,现在你已经find了SlickGrid,我确信这些filter的需求变得非常明显。
我可以很确定地说,你真的不需要向用户显示数百万行的数据。
世界上没有哪个用户能够理解或pipe理这个数据集,所以即使你在技术上能够把它解决掉,你也不会为那个用户解决任何已知的问题。
相反,我会把重点放在为什么用户希望看到数据。 用户不希望看到数据只是为了查看数据,通常会有一个问题被问到。 如果你专注于回答这些问题,那么你会更接近解决实际问题的东西。
我推荐具有缓冲视图function的Ext JS Grid。
dojox.grid.DataGrid提供了一个JS抽象的数据,所以你可以通过提供的dojo.data存储挂钩到不同的后端或者自己写。 你显然需要一个支持随机访问的logging。 DataGrid还提供了完整的可访问性。
编辑所以这里有一个链接到马修·罗素的文章 ,应该提供你需要的例子,用dojox.grid查看数百万条logging。 请注意,它使用网格的旧版本,但概念是相同的,只是有一些不兼容的API改进。
哦,这是完全免费的开源。
(免责声明:我是w2ui的作者)
我最近写了一篇关于如何实现百万条logging的JavaScript网格的文章( http://w2ui.com/web/blog/7/JavaScript-Grid-with-One-Million-Records )。 我发现,最终有3个限制,防止采取更高:
- div的高度有一个限制(可以通过虚拟滚动来克服)
- sorting和search等操作在100万条左右之后开始缓慢
- RAM是有限的,因为数据存储在JavaScript数组中
我已经testing了100万条logging(IE除外)的网格,并且performance良好。 请参阅文章的演示和示例。
我使用jQuery Grid Plugin ,这很好。
演示
这里有几个优化,你可以应用你加速的东西。 只是大声思考。
由于行数可能在几百万,所以你只需要一个caching系统来从服务器获取JSON数据。 我无法想象任何人想要下载所有的X百万条目,但如果他们这样做,这将是一个问题。 对于20M +整数数组的Chrome这个小testing不断在我的机器上崩溃。
var data = []; for(var i = 0; i < 20000000; i++) { data.push(i); } console.log(data.length);
您可以使用LRU或其他一些cachingalgorithm,并对您愿意caching多less数据有一个上限。
对于表格单元格本身,我认为构build/销毁DOM节点可能很昂贵。 相反,您可以预先定义X个单元格,并且每当用户滚动到一个新位置时,将JSON数据注入到这些单元格中。 滚动条实际上与代表整个数据集需要多less空间(高度)没有直接关系。 你可以任意设置表格容器的高度,比如说5000px,并将其映射到总行数。 例如,如果容器高度是5000px,并且总共有10M行,则starting row ≈ (scroll.top/5000) * 10M
其中, scroll.top
表示从容器顶部的滚动距离。 小演示在这里 。
为了检测何时请求更多的数据,理想情况下,一个对象应该作为一个中介来监听滚动事件。 该对象跟踪用户滚动的速度,当用户看起来像正在减速或已经完全停止时,会对相应的行进行数据请求。 以这种方式检索数据意味着你的数据将被分割,所以应该考虑到caching的devise。
浏览器对最大传出连接的限制也可以起到重要的作用。 用户可以滚动到某个会触发AJAX请求的位置,但在此之前,用户可以滚动到其他部分。 如果服务器没有足够的响应,请求将会排队,应用程序看起来没有反应。 您可以使用一个请求pipe理器,通过它来路由所有请求,并且可以取消挂起的请求以腾出空间。
我知道这是一个老问题,但仍然..也有dhtmlxGrid ,可以处理数百万行。 有一个50,000行的演示,但可以在网格中加载/处理的行数是无限的。
免责声明:我来自DHTMLX团队。
我build议你阅读这个
免责声明:我长时间 大量使用YUI DataTable 。 它强大而稳定。 为了您的需要,您可以使用一个ScrollingDataTable这个suports
- X-滚动
- Y型滚动
- XY-滚动
- 强大的事件机制
对于你所需要的,我想你想要的是一个tableScrollEvent 。 其API说
固定滚动的DataTable滚动时触发。
由于每个DataTable都使用一个DataSource, 所以可以通过tableScrollEvent 监视其数据 以及渲染循环的大小 ,以便根据需要填充ScrollingDataTable。
渲染循环大小说
如果您的DataTable需要显示一大组数据, 则renderLoopSizeconfiguration可以帮助pipe理浏览器DOM呈现,以便UI线程不会locking在非常大的表上 。 任何大于0的值都将导致在每个循环中呈现指定行数的setTimeout()链中执行DOM渲染。 由于没有硬性和快速的规则,只有一般的指导原则,每个实施应该确定理想的价值:
- 默认情况下,renderLoopSize是0,所以所有的行都在一个循环中呈现。 renderLoopSize> 0会增加开销,所以请谨慎使用。
- 如果您的数据集足够大 (X行数X行X格式化复杂度),用户在视觉渲染中遇到延迟并且/或者导致脚本挂起,请考虑设置renderLoopSize 。
- 一个低于50的renderLoopSize可能是不值得的。 renderLoopSize> 100可能更好。
- 数据集可能不被认为是足够大,除非它有成百上千的行。
- renderLoopSize> 0和<total rows确实会导致表在一个循环中呈现(与renderLoopSize = 0相同),但是它也会触发一些function,例如从单独的setTimeout线程处理后置渲染行条带。
例如
// Render 100 rows per loop var dt = new YAHOO.widget.DataTable(<WHICH_DIV_WILL_STORE_YOUR_DATATABLE>, <HOW YOUR_TABLE_IS STRUCTURED>, <WHERE_DOES_THE_DATA_COME_FROM>, { renderLoopSize:100 });
<WHERE_DOES_THE_DATA_COME_FROM>只是一个数据源 。 它可以是JSON,JSFunction,XML甚至单个HTML元素
在这里你可以看到一个简单的教程,由我提供。 请注意, 其他的 DATA_TABLE插件不能同时支持单击和双击。 YUI DataTable允许你。 而且, 甚至可以在没有头痛的情况下使用JQuery
一些例子,你可以看到
- 列表项目
随意质疑关于YUI DataTable的其他任何事情。
问候,
我有点不明白的地方,因为jqGrid你可以使用虚拟滚动function:
http://www.trirand.net/aspnetmvc/grid/performancevirtualscrolling
但是再一次,可以完成数百万行过滤:
http://www.trirand.net/aspnetmvc/grid/performancelinq
虽然我没有看到“好像没有页面”的意思,但是我的意思是……在浏览器中无法一次显示1,000,000行 – 这是10MB的HTML raw,我有点看不懂为什么用户不想看到页面。
无论如何…
我能想到的最好的方法是在滚动结束之前,为每个滚动或某个限制加载json格式的数据块。 JSON可以很容易地转换为对象,因此表格行可以轻松地构造
我会极力推荐Open rico 。 一开始就很难实现,但是一旦抓住它就永远不会回头。
我知道这个问题是几年,但现在jqgrid支持虚拟滚动:
http://www.trirand.com/blog/phpjqgrid/examples/paging/scrollbar/default.php
但禁用了分页
我build议西格玛网格,西格玛网格embedded了可以支持数百万行的分页function。 此外,您可能需要远程分页才能完成。 请参阅演示http://www.sigmawidgets.com/products/sigma_grid2/demos/example_master_details.html
看看dGrid:
http://dojofoundation.org/packages/dgrid/
我同意,用户将永远不会,一次需要查看数百万行数据,但dGrid可以快速显示(一次屏幕)。
不要烧开海洋来喝杯茶。