Tengo un archivo de texto con dos oraciones, una en la línea 1 y la otra oración en la línea 2
Ejemplo:
línea 1: El foo es negro
línea 2: La barra ladra
El contenido de la línea 1 y la línea 2 se colocaría dentro de una matriz
ejemplo: ['The foo is black', 'The bar barks']
Ahora que tengo estos dos dentro de una matriz, quiero recorrer la matriz y colocar cada word en la oración dentro de un objeto junto con el número de línea en el que se encuentra. Ejemplo:
{
barks : 2 //line 2
black : 1 //line 1
foo: 1
bar: 2
is : 1
the : 1, 2
}
¿Cómo puedo abordar esto? Pensé que podría recorrer la matriz y luego agregar cada word a un objeto, pero la salida no necesariamente tiene que estar en un objeto, solo fue mi pensamiento. Es importante tener en cuenta que la salida también debe ordenarse en orden alfabético.
Creo que el mejor enfoque es seguir con una matriz, que en realidad puede ordenar ( Map resultará difícil si tiene la misma word en varias líneas).
Ver este proceso:
const data = ['The foo is black', 'The bar barks'];
let output = new Array();
data.forEach((i, line) => {
line++; // because line numbers start from 1
// split into words lowercase and include line number
const words = i.split(' ').map(j => j.toLowerCase()).map(text => ({
text,
line
}));
output.push(...words);
});
// sort alphabetically
output = output.sort((a, b) => (+(a.text > b.text) || -1));
console.log('Data sorted alphabetically with line numbers:', output);
Como el orden es importante, el resultado final debería ser una matriz de pares. Y dado que una word puede aparecer varias veces en la misma cadena, puede ser interesante no solo mencionar el número de línea, sino también el número de la word en esa línea:
function wordOccurrences(lines) {
const obj = {};
lines.forEach((lineStr, line) =>
lineStr.toLowerCase().match(/\S+/g).forEach((wordStr, word) =>
(obj[wordStr] ??= []).push({line, word})
)
);
const result = Object.entries(obj).sort(([a], [b]) => a.localeCompare(b));
return result;
}
const result = wordOccurrences(['The foo is black', 'The bar barks']);
console.log(result);
Usando un Map , puedes hacer esto:
const lines = ['The foo is black', 'The bar barks'];
let wordCount = new Map();
for (let i = 0; i < lines.length; i++) {
const words = lines[i].split(' ');
for (const word of words) {
let count = wordCount.get(word.toLowerCase()) || [];
count.push(i + 1);
wordCount.set(word.toLowerCase(), count);
}
}
wordCount = new Map([...wordCount.entries()].sort());
console.log(wordCount);
Creo que esta es la forma más comprensible e idiomática de hacer esto.