100
  1. indexedDB 和本地存储都是键值存储。拥有两个键/值存储有什么好处?
  2. indexedDB 是异步的,但连接(最耗时的事情)是手动的。它们似乎在进行异步调用的同一线程中运行。这怎么不会阻塞用户界面?
  3. indexedDB 允许更大的存储。为什么不增加 HTML5 商店的大小?
  4. 我在挠头。indexedDB 的意义何在?
4

4 回答 4

140

IndexedDB 不像本地存储那样是键值存储。本地存储只存储字符串,因此要将对象放入本地存储,通常的方法是JSON.stringify它:

myObject = {a: 1, b: 2, c: 3};
localStorage.setItem("uniq", JSON.stringify(myObject));

这对于使用 key 查找对象很好uniq,但是从本地存储中获取 myObject 属性的唯一方法是 JSON.parse 对象并检查它:

var myStorageObject = JSON.parse(localStorage.getItem("uniq"));
window.alert(myStorageObject.b);

如果您在本地存储中只有一个或几个对象,这很好。但是想象一下,你有一千个对象,它们都有一个属性b,而你想对那些 where 做一些事情b==2。使用本地存储,您将不得不遍历整个商店并检查b每个项目,这会浪费大量的处理时间。

使用 IndexedDB,您可以在 value 中存储字符串以外的内容:“这包括简单类型,例如 DOMString 和 Date 以及 Object 和 Array 实例。” 不仅如此,您还可以为存储在值中的对象的属性创建索引。因此,使用 IndexedDb,您可以将相同的数千个对象放入其中,但在b属性上创建一个索引并使用它来检索对象,b==2而无需扫描存储中的每个对象的开销。

至少是这样的想法。IndexedDB API 不是很直观。

它们似乎在进行异步调用的同一线程中运行。这怎么不会阻塞用户界面?

异步与多线程不同,JavaScript 通常不是多线程的如果您想尽量减少对 UI 的阻塞,请尝试Web Workers,您在 JS 中执行的任何繁重处理都会阻塞 UI 。

indexedDB 允许更大的存储。为什么不增加 HTML5 商店的大小?

因为,如果没有适当的索引,它越大越慢。

于 2011-05-07T23:54:38.463 回答
14

我遇到了这篇讨论 localstorage vs indexeddb 和其他可能选项的好文章。

(以下所有值均以毫秒为单位)

https://nolanlawson.com/2015/09/29/indexeddb-websql-localstorage-what-blocks-the-dom/

内存比较

从文章中总结(完全是作者的观点),

  1. 在 Chrome、Firefox 和 Edge 的所有三个中,LocalStorage 在您写入数据时完全阻塞 DOM 2。阻塞比内存中更明显,因为浏览器必须实际刷新到磁盘。
  2. 毫不奇怪,由于任何同步代码都是阻塞的,内存中的操作也是阻塞的。DOM 在长时间运行的插入过程中会阻塞,但除非您处理大量数据,否则您不太可能注意到,因为内存中的操作非常快。
  3. 在 Firefox 和 Chrome 中,IndexedDB 在基本键值插入方面都比 LocalStorage 慢,而且它仍然会阻塞 DOM。在 Chrome 中,它也比阻止 DOM 的 WebSQL 慢,但几乎没有那么多。只有在 Edge 和 Safari 中,IndexedDB 才能在后台运行而不中断 UI,更糟糕的是,这两个浏览器只部分实现了 IndexedDB 规范。

  4. IndexedDB 在 web worker 中运行良好,它以大致相同的速度运行,但不会阻塞 DOM。唯一的例外是 Safari,它不支持 worker 内部的 IndexedDB,但它仍然不会阻塞 UI。

  5. 如果数据简单且最少,则 localmemory 是理想的

于 2018-03-20T05:32:16.363 回答
6

添加到 robertc 的 anwser 中,indexedDB 知道“范围”,因此您可以搜索和检索所有以“ab”开头并以 abd 结尾的记录以查找“abc”等。

于 2011-07-01T07:00:41.743 回答
0

在浏览器的控制台中运行以下命令。它将在 Application > Storage 以及 LocalStorage 和 SessionStorage 中创建一个单独的实体

const request = indexedDB.open("notes");
request.onupgradeneeded = e => {
  alert("upgrade");
}
request.onsuccess = e => {
  alert("success");
}
request.onerror = e => {
  alert("error");
}

您可以使用所有 CRUD 操作来查询此存储,这与其他两个存储的灵活性和功能较差的存储不同。

于 2019-07-21T07:41:41.897 回答