性能问题 - 如果我有两个相互排斥的视图(例如成功通知/失败通知) - 从性能角度来看,最好使用:
1)parentView.removeView(indexOfChild)
和addView()
两者之间的过渡
2)覆盖两个视图并切换它们的可见性
3) 使用ViewSwitcher
性能问题 - 如果我有两个相互排斥的视图(例如成功通知/失败通知) - 从性能角度来看,最好使用:
1)parentView.removeView(indexOfChild)
和addView()
两者之间的过渡
2)覆盖两个视图并切换它们的可见性
3) 使用ViewSwitcher
我进行了一项小型研究以找出答案。简而言之 - 改变可见性会更好。
结果是(以毫秒为单位,平均估计):
HTC Desire (4.0.4)
TEST1(visibility) = 251.5
TEST2(movement) = 751.1
TEST3(ViewSwitcher) = 267.0
HTC Wildfire (2.3.5)
TEST1(visibility) = 285.0
TEST2(movement) = 172.7
TEST3(ViewSwitcher) = 302.1
Samsung GALAXY S3 (4.1.2)
TEST1(visibility) = 83.5
TEST2(movement) = 3364.9
TEST3(ViewSwitcher) = 108.7
Google Nexus 4 (4.3)
TEST1(visibility) = 101.7
TEST2(movement) = 380.7
TEST3(ViewSwitcher) = 126.9
测试代码:
public class MainActivity extends Activity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
test2View1 = findViewById(R.id.move_test1);
test2View2 = findViewById(R.id.move_test2);
findViewById(R.id.button1_start).setOnClickListener(
new OnClickListener() {
@Override
public void onClick(View v) {
final int totalExpCount = 10;
final double[] totalResult = new double[3];
for (int i = 0; i < totalExpCount; i++) {
final long[] currentResult = performanceTest();
for (int j = 0; j < 3; j++) {
totalResult[j] += currentResult[j];
}
}
for (int j = 0; j < 3; j++) {
totalResult[j] /= totalExpCount;
}
Log.i("TIMING",
"=========================================");
Log.i("TIMING", "TOTAL - TEST1(visibility) = "
+ totalResult[0]);
Log.i("TIMING", "TOTAL - TEST2(movement) = "
+ totalResult[1]);
Log.i("TIMING", "TOTAL - TEST3(ViewSwitcher) = "
+ totalResult[2]);
}
});
}
View test2View1;
View test2View2;
private final long[] performanceTest() {
final int testCount = 10000;
// test 1
final View test1View1 = findViewById(R.id.visibility_test1);
final View test1View2 = findViewById(R.id.visibility_test2);
final long test1StartTime = System.currentTimeMillis();
for (int i = 0; i < testCount; i++) {
final int visibility = test1View1.getVisibility();
test1View1.setVisibility(test1View2.getVisibility());
test1View2.setVisibility(visibility);
}
final long test1EndTime = System.currentTimeMillis();
final long test1ResultTime = test1EndTime - test1StartTime;
// test 2
final ViewGroup test2ParentView = (ViewGroup) findViewById(R.id.layout_test2);
test2ParentView.removeAllViews();
test2ParentView.addView(test2View1);
final long test2StartTime = System.currentTimeMillis();
for (int i = 0; i < testCount; i++) {
if ((i % 2) == 0) {
test2ParentView.addView(test2View2);
test2ParentView.removeView(test2View1);
} else {
test2ParentView.addView(test2View1);
test2ParentView.removeView(test2View2);
}
}
final long test2EndTime = System.currentTimeMillis();
final long test2ResultTime = test2EndTime - test2StartTime;
// test 3
final ViewSwitcher test3ParentView = (ViewSwitcher) findViewById(R.id.layout_test3);
test3ParentView.reset();
final long test3StartTime = System.currentTimeMillis();
for (int i = 0; i < testCount; i++) {
test3ParentView.showNext();
}
final long test3EndTime = System.currentTimeMillis();
final long test3ResultTime = test3EndTime - test3StartTime;
Log.i("TIMING", "-----------------------------------------");
Log.i("TIMING", "TEST1(visibility) = " + test1ResultTime);
Log.i("TIMING", "TEST2(movement) = " + test2ResultTime);
Log.i("TIMING", "TEST3(ViewSwitcher) = " + test3ResultTime);
final long[] result = new long[3];
result[0] = test1ResultTime;
result[1] = test2ResultTime;
result[2] = test3ResultTime;
return result;
}
}
和 XML:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context=".MainActivity" >
<Button
android:id="@+id/button1_start"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Start test" />
<RelativeLayout
android:id="@+id/layout_test1"
android:layout_width="wrap_content"
android:layout_height="wrap_content" >
<TextView
android:id="@+id/visibility_test1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="one" />
<TextView
android:id="@+id/visibility_test2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="two"
android:visibility="gone" />
</RelativeLayout>
<RelativeLayout
android:id="@+id/layout_test2"
android:layout_width="wrap_content"
android:layout_height="wrap_content" >
<TextView
android:id="@+id/move_test1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="one" />
<TextView
android:id="@+id/move_test2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="two" />
</RelativeLayout>
<ViewSwitcher
android:id="@+id/layout_test3"
android:layout_width="wrap_content"
android:layout_height="wrap_content" >
<TextView
android:id="@+id/switcher_test1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="one" />
<TextView
android:id="@+id/switcher_test2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="two" />
</ViewSwitcher>
</LinearLayout>