简体   繁体   English

通过对象进行JavaScript搜索

[英]Javascript search through object

I'm unfortunately still not quite familiar with objects in JS and only programming a bit for my PhD in psychology, so I don't have great programming skills. 不幸的是,我仍然不太熟悉JS中的对象,只为心理学博士学位编程,所以我没有很好的编程技能。 I've managed to create a nice object which captures my data structure pretty well: 我设法创建了一个很好的对象,它很好地捕获了我的数据结构:

var items = {
  anamnese_akut: [{
    id: 1,
    question: 'Haben Sie die Beschwerden zum ersten Mal?',
    answer: 'Ja, also so etwas ist noch nie passiert.'
  }, {
    id: 2,
    question: 'Haben Sie in den letzten Wochen unbeabsichtigt Gewicht verloren?',
    answer: 'Nein, bestimmt nicht.'
  }],
  anamnese_allgemein: [{
    id: 3,
    question: 'Sind bei Ihnen Vorerkrankungen bekannt?',
    answer: 'Eigentlich nicht, nein.'
  }, {
    id: 4,
    question: 'Wurden Sie schon mal operiert?',
    answer: 'Ich hatte eine Blinddarmoperation als Kind, und in den letzten zwei Jahren dreimal eine Ausschabung nach Fehlgeburten.'
  }]
};    

I now want to search for an input variable which contains exactly one of these 4 questions, but can come from both categories. 现在,我想搜索一个输入变量,该变量恰好包含这四个问题之一,但可以同时来自这两个类别。 I've already managed to do something like this with an unnested object, using the code from here: JS search in object values , but I cannot get it to work and have no idea how to adapt it to an object with categories like anamnese_akut and anamnese_allgemein . 我已经设法使用下面的代码对一个未嵌套的对象执行类似的操作: JS搜索对象值 ,但是我无法使其正常工作,也不知道如何将其适应于具有anamnese_akutanamnese_allgemein

How can I adapt a search for this? 如何调整搜索范围? After comparing the input with the questions I want to have an index, so that I can give an output of the corresponding answer to the found question. 在将输入与问题进行比较之后,我想要一个索引,以便可以为找到的问题提供相应答案的输出。

I think there is another way of structuring your data here. 我认为这里还有另一种结构化数据的方式。 You can avoid arrays and use referencing by object properties . 您可以避免使用数组,而是使用对象属性进行引用 The advantage is, that you can access the values without a "search" in terms of iterations but by the object's property hash. 好处是,您无需进行“搜索”即可访问值,而可以通过对象的属性哈希来进行“搜索”。

Note: for readability purposes, I have only used a reduced subset of your data in the examples. 注意:出于可读性目的,在示例中,我仅使用了一部分数据。

Example A - Base on index number 示例A-基于索引号

 var anamnese_akut = { q: { 1:'Haben Sie die Beschwerden zum ersten Mal?', 2: 'Haben Sie in den letzten Wochen unbeabsichtigt Gewicht verloren?', }, a: { 1:'Ja, also so etwas ist noch nie passiert.', 2:'Nein, bestimmt nicht.' }, }; console.log(anamnese_akut.q['1']); console.log(anamnese_akut.a['1']); 

With this example you would base your data on the index number (1, 2, 3...) and access your questions and answers by that number. 在此示例中,您将以索引号(1、2、3 ...)为基础建立数据,并根据该索引访问问题和答案。

Advantage: Less error prone, because the index is short and can be stored as number. 优点:错误少,因为索引很短并且可以存储为数字。

Disadvantage: Index number must be known within overall context of q and a. 缺点:必须在q和a的整体上下文中知道索引号。

Example B - Access by Id but with different structure 示例B-通过ID进行访问,但结构不同

 var questions = { anamnese_akut: { 1:'Haben Sie die Beschwerden zum ersten Mal?', 2:'Haben Sie in den letzten Wochen unbeabsichtigt Gewicht verloren?', }, }; var answers = { anamnese_akut: { 1: 'Ja, also so etwas ist noch nie passiert.', 2: 'Nein, bestimmt nicht.', }, }; console.log(questions.anamnese_akut['1']); console.log(answers.anamnese_akut['1']); 

Advantages: Decoupled questions and answers, for access only the index is required (as in Example A) 优点:解耦的问题和答案,仅需索引即可访问(如示例A中所示)

Disadvantage: More work on the structural design level, since there is a little bit more redundancy here (since we have now two objects with the anamnese_akut entry). 缺点:在结构设计级别上需要做更多的工作,因为这里有更多的冗余(因为我们现在有两个对象带有anamnese_akut条目)。

Example C - Access by question 示例C-按问题访问

 var anamnese_akut = { 'Haben Sie die Beschwerden zum ersten Mal?' : 'Ja, also so etwas ist noch nie passiert.', }; console.log(anamnese_akut['Haben Sie die Beschwerden zum ersten Mal?']); 

Advantages: Answer immediatly returned 优点:立即返回答案

Disadvantage: Question string needs to be strictly as given in the object or the access fails and returns undefined. 缺点:问题字符串必须严格按照对象中的给出,否则访问将失败并返回未定义。

Personally I would go for Example B since it allows me to split question and answer data contexts (which may become important, depending on your application use case) and still allows me to access by one given index number. 我个人将使用示例B,因为它允许我拆分问题和答案数据上下文(这可能很重要,具体取决于您的应用程序使用情况),并且仍然允许我按给定的索引号进行访问。

If I take your meaning correctly: your input is question text and it needs to be matched to one of these objects, then this should do the trick: 如果我正确理解了您的意思:您的输入是问题文本,并且需要与这些对象之一匹配,那么这应该可以解决问题:

var input = 'Haben Sie die Beschwerden zum ersten Mal?' // For demo purposes.
var output = items.anamnese_akut.find(x => x.question === input) || items.anamnese_allgemein.find(x => x.question === input)

Of course this isn't the most elegant solution, especially if you add more anamnese objects. 当然,这不是最优雅的解决方案,尤其是如果您添加更多的anamnese对象。

you can do it in the following way 您可以通过以下方式进行

 var items = { anamnese_akut: [{ id: 1, question: 'Haben Sie die Beschwerden zum ersten Mal?', answer: 'Ja, also so etwas ist noch nie passiert.' }, { id: 2, question: 'Haben Sie in den letzten Wochen unbeabsichtigt Gewicht verloren?', answer: 'Nein, bestimmt nicht.' }], anamnese_allgemein: [{ id: 3, question: 'Sind bei Ihnen Vorerkrankungen bekannt?', answer: 'Eigentlich nicht, nein.' }, { id: 4, question: 'Wurden Sie schon mal operiert?', answer: 'Ich hatte eine Blinddarmoperation als Kind, und in den letzten zwei Jahren dreimal eine Ausschabung nach Fehlgeburten.' }] }; let query = 'Wurden Sie schon mal operiert?'; let answer = Object.keys(items).reduce(function(a, b){ let val = items[b].reduce(function(a, b){ if(b.question == query){ return b.answer; } }, "not available") if(val == "not available") return a; return val; }, "not available"); console.log(answer); 

const input = "whatever";

for(const category in items){
 for(const question of items[category]){
   if(question.question === input){
     //do whatever
     //optionally: return; 
   }
 }
}

In action 在行动

or if you prefer a functional approach: 或者,如果您更喜欢功能性方法:

const input = "whatever";
const result = Object.values(items).reduce(
   (res,category)=> res || category.find(obj => obj.question === input ), false
);

In action 在行动

For getting the category and the index of the inner array, you could oiterate the keys of the given object an then iterate the inner array for checking the questions. 为了获得内部数组的类别和索引,您可以省略给定对象的键,然后迭代内部数组以检查问题。 If the given string is equal to a question property, then the actual category and index is returned. 如果给定的字符串等于问题属性,则返回实际的类别和索引。 If no result is found, undefined is returned. 如果未找到结果,则返回undefined

 function find(object, search) { var result; Object.keys(object).some(function (k) { return object[k].some(function (o, i) { if (o.question === search) { result = { category: k, index: i }; return true; } }); }); return result; } var items = { anamnese_akut: [{ id: 1, question: 'Haben Sie die Beschwerden zum ersten Mal?', answer: 'Ja, also so etwas ist noch nie passiert.' }, { id: 2, question: 'Haben Sie in den letzten Wochen unbeabsichtigt Gewicht verloren?', answer: 'Nein, bestimmt nicht.' }], anamnese_allgemein: [{ id: 3, question: 'Sind bei Ihnen Vorerkrankungen bekannt?', answer: 'Eigentlich nicht, nein.' }, { id: 4, question: 'Wurden Sie schon mal operiert?', answer: 'Ich hatte eine Blinddarmoperation als Kind, und in den letzten zwei Jahren dreimal eine Ausschabung nach Fehlgeburten.' }] }; console.log(find(items, 'Sind bei Ihnen Vorerkrankungen bekannt?')); 
 .as-console-wrapper { max-height: 100% !important; top: 0; } 

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM