我使用了以下代码:
mp = MediaPlayer.create(this, Uri.parse("file://"+filePath));
mp.start();
这很好用。然后我想播放文件夹中的音乐
mp.setDataSource(this, Uri.parse("file://"+filePath));
mp.prepareAsync();
mp.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {
@Override
public void onPrepared(MediaPlayer mp) {
mp.start();
}
});
这两种方法之间是否有任何性能差异?
答案 0 :(得分:3)
第一种方法绑定了你所使用的任何线程,足以使MediaPlayer
读取媒体的元数据并准备一些缓冲区。如果这是主应用程序线程,则意味着您的UI将在此过程中被冻结。
答案 1 :(得分:3)
您可以查看MediaPlayer
create() source code以查看差异:
public static MediaPlayer create(Context context, Uri uri, SurfaceHolder holder,
AudioAttributes audioAttributes, int audioSessionId) {
try {
MediaPlayer mp = new MediaPlayer();
final AudioAttributes aa = audioAttributes != null ? audioAttributes :
new AudioAttributes.Builder().build();
mp.setAudioAttributes(aa);
mp.setAudioSessionId(audioSessionId);
mp.setDataSource(context, uri);
if (holder != null) {
mp.setDisplay(holder);
}
mp.prepare();
return mp;
} catch (IOException ex) {
Log.d(TAG, "create failed:", ex);
// fall through
} catch (IllegalArgumentException ex) {
Log.d(TAG, "create failed:", ex);
// fall through
} catch (SecurityException ex) {
Log.d(TAG, "create failed:", ex);
// fall through
}
return null;
}
基本上create()
调用是同步的(内部调用prepare()
),prepareAsync()
是异步的。
答案 2 :(得分:2)
当然,在主线程中创建方法inits对象。所以它下面的代码行应该等待创建。
另一方面,prepare asynchronous打开一个新的线程到init对象,然后通知你在主线程运行其他行时运行下一个操作。
修改:正如评论中提到的@CommonWares,mp.create()
是一种同时调用mp.setDataSoucer()
+ mp.prepare()
的便捷方法