我正在用javascript构建歌曲播放列表。我使用了一个关联数组foo
- 我的对象的结构看起来类似于:
foo[songID] = songURL;
我正在尝试构建改组功能。我想从这个列表中随机选择一首歌。有没有一种简单的方法 - 数组没有索引。
答案 0 :(得分:9)
您可以使用函数Object.keys(object)
来获取对象键的数组。可以在MDN找到关于此功能的非常好的文档。
您似乎也有两个不同但相关的问题。
您的主题询问如何从对象中获取随机元素。为此,
var randomProperty = function (object) {
var keys = Object.keys(object);
return object[keys[Math.floor(keys.length * Math.random())]];
};
但你也在问题正文中询问如何改组阵列。为此,你需要某种shuffle函数(很可能是Fischer-Yates的一个实现),并直接这样做。
var objectKeysShuffled = function (object) {
return shuffle(Object.keys(object));
};
答案 1 :(得分:2)
这是我从音频元素的散列中播放随机背景歌曲的功能。
this.bgm = {} //I later added audio elements to this
this.playRandomBGM = function()
{
var keys = Object.keys(this.bgm);
self.currentBGM = keys[Math.floor(keys.length * Math.random())];
console.log("Playing random BGM: " + self.currentBGM);
self.bgm[self.currentBGM].play();
}
答案 2 :(得分:0)
您可以尝试这样的事情:
var obj = {
'song1': 'http://...1',
'song2': 'http://...2',
'song3': 'http://...3',
'song4': 'http://...4',
'song5': 'http://...5',
'song6': 'http://...6',
}, tempArr = [], len, rand, song;
for ( var key in obj )
if ( obj.hasOwnProperty(key) )
tempArr.push( obj[key] );
len = tempArr.length;
rand = Math.floor( Math.random() * len );
song = tempArr[rand];
document.write(song);
请注意,这实际上只是一种愚蠢的方式来绕过这样的事实:这个东西应该是一个具有这样结构的数组:
var songs = [
{title: 'Song1', url: 'http://...1.mp3'},
{title: 'Song2', url: 'http://...2.mp3'},
{title: 'Song3', url: 'http://...3.mp3'}
];
答案 3 :(得分:0)
function fetchRandom(arr) {
var ret,
i = 0;
for (var key in arr){
if (Math.random() < 1/++i){
ret = key;
}
}
return ret;
}
var randomSong = foo[fetchRandom(foo)];
你应该使用一个对象。然后使用索引的对象数组进行随机化,但这应该回答你的问题。
答案 4 :(得分:0)
效率低下的方法是:
function randomProperty(obj) {
var a = [];
for (var p in obj) {
if (obj.hasOwnProperty(p)) {
a.push(p);
}
}
return a.length? obj[ a[a.length * Math.random() | 0]] : void 0;
}
正如其他人所说的那样,更有效地存储属性名称数组并重新使用它,而不是每次都使用它。