Reputation: 73015
I'm using Node.js to load an array of files from a folder and create an array of objects:
var files = {}
fs.readdirSync(dir).forEach(function(file) {
files[file] = fs.readFileSync(dir + '/' + file)
})
This seems like I should be able to do this without defining the object first, using .map()
maybe?
Upvotes: 2
Views: 227
Reputation: 82307
Using map won't reproduce your example. It will construct an array of objects. This entire exercise is essentially a micro optimization and what you have works and is readable so I would suggest just using it.
That said, you could move the object definition if you really wanted to, and I will show a small example here of that just to show options
var files = fs.readdirSync(dir).reduce(function(obj,file) {
return (obj[file] = fs.readFileSync(dir + '/' + file),obj)
},{})
Upvotes: 1
Reputation: 32511
As others have mentioned, you could do it with this (arguably uglier) reduce
.
var files = fs.readdirSync(dir).reduce(function(files, file) {
files[file] = fs.readFileSync(dir + '/' + file);
return files;
}, {});
To make this nicer to use, you could wrap it in a helper function or even extend the Array prototype (not suggested but it does look cleaner).
function log(msg) {
document.querySelector('pre').innerText += msg + '\n';
}
var filesInDir = ['a.txt', 'b.txt', 'c.txt'];
var files;
// Helper function
function toObject(arr, map) {
return arr.reduce(function(obj, value) {
obj[value] = map(value);
return obj;
}, {});
};
files = toObject(filesInDir, function(file) {
return file + '_mapped';
});
log('Helper');
log(JSON.stringify(files, null, 2));
// Modify the prototype (not recommended)
Array.prototype.toObject = function(map) {
return this.reduce(function(obj, value) {
obj[value] = map(value);
return obj;
}, {});
};
files = filesInDir.toObject(function(file) {
return file + '_mapped';
});
log('Prototype');
log(JSON.stringify(files, null, 2));
<pre></pre>
Upvotes: 0
Reputation:
In theory you could do
Object.assign({}, ...fs.readdirSync(dir) .
map(
file => ({[file]: fs.readFileSync(dir + '/' + file})
)
);
Whether or not that is more "concise" is up to you.
The reduce solution would be
fs.readdirSync(dir) .
reduce(
(result, file) => {
result[file] = fs.readFileSync(dir + '/' + file);
return result;
},
{}
);
or
fs.readdirSync(dir) .
reduce(
(result, file) =>
result.defineProperty(file, {
value: fs.readFileSync(dir + '/' + file)
}),
{}
);
None of these seems as obvious as the code you propose.
Underscore can transform an array of pairs into an object, so you could do
_.object(fs.readdirSync(dir) .
map(
file =>
[file, fs.readFileSync(dir + '/' + file]
)
);
Upvotes: 0