在网上看见View.findViewById() 和 Activity.findViewById()执行效率不一样

使用Activity.findViewById()如:

TextView tv_inner_1 = (TextView)this.findViewById(R.id.tv_inner_1);
TextView tv_inner_2 = (TextView)this.findViewById(R.id.tv_inner_2);

使用View.findViewById() 如:

View layout_outer = this.findViewById(R.id.layout_outer);
TextView tv_inner_1 = (TextView)layout_outer.findViewById(R.id.tv_inner_1);
TextView tv_inner_2 = (TextView)layout_outer.findViewById(R.id.tv_inner_2);

他们都是针对下面同一个xml

    <LinearLayout>
<LinearLayout id="@+id/layout_outer">
<TextView id="@+id/tv_inner_1"/>
<TextView id="@+id/tv_inner_2"/>
</LinearLayout>
</LinearLayout>

自从学习android的hello world开始

我们就知道了这样一个函数findViewById(),他已经成为了家喻户晓,坑蒙拐骗,杀人越货必备的一个函数(好吧,这句是扯淡)

但一直用也没细致研究过它,直到写程序的时候发现一个由这个函数引起的一个莫名其妙的bug,遂决定好好研究下次函数~

我们调用的findViewById()函数其实有两种(目前我只看到两种,不确定还有没有其他的),一种是Activity类中findViewById()函数

另外一种是View类中定义的findViewById()函数

一般我们在oncreate()方法中使用的(**view)findViewById(R.id.**)既是调用的Activity中的findViewById()函数

而在其他情况写出的***view.findViewById()中调用的是view类中的findViewById()

分别看一下源代码中的实现方法及介绍

Activity类中定义的findViewById()

/**
* Finds a view that was identified by the id attribute from the XML that
* was processed in {@link #onCreate}.
*
* @return The view if found or null otherwise.
*/
public View findViewById(int id) {
return getWindow().findViewById(id);
}
/**
* Retrieve the current {@link android.view.Window} for the activity.
* This can be used to directly access parts of the Window API that
* are not available through Activity/Screen.
*
* @return Window The current window, or null if the activity is not
* visual.
*/
public Window getWindow() {
return mWindow;
}

这里可以看出这个函数是在寻找在xml中定义的指定id的对象

View类中的findViewById()

/**
* Look for a child view with the given id. If this view has the given
* id, return this view.
*
* @param id The id to search for.
* @return The view that has the given id in the hierarchy or null
*/
public final View findViewById(int id) {
if (id < 0) {
return null;
}
return findViewTraversal(id);
/**
* {@hide}
* @param id the id of the view to be found
* @return the view of the specified id, null if cannot be found
*/
protected View findViewTraversal(int id) {
if (id == mID) {
return this;
}
return null;
}

从这里可以看出我们是从一个view的child view中寻找指定id的对象,所以即使几个layout的XML文件中的View的id号相同的话,只要他们没有相同的父节点,或有相同的父亲节点,但不在父节点及以上节点调用findViewById通过id来查找他们就是没有问题。(这句引用自这里http://www.2cto.com/kf/201204/127404.html
使用这个函数的常见问题:
1.既然Activity中的findViewById()是从R.java中寻找东西,那么我们就要杜绝相同名字的控件
今天自己的bug就是因为这个产生的

说到控件的命名,今天还有一个小发现

仔细看下边两段代码代码

< ?xml version="1.0" encoding="utf-8"?>
< LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/LinearLayout"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
< /LinearLayout>
< ?xml version="1.0" encoding="utf-8"?>
< LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
< /LinearLayout>

一段里边Layout没有id这个参数,一段里边有id,虽然代码不同但在outline中显示出来都是

这样在第一种情况下R.id中可以找到LinearLayout这个控件,第二种是没有的哈,这些也是以后要注意的细节

2.在调用view中的findViewById()一定要想好父View是谁!即**view.findViewById()中的**view要找对,如果没有找对父View,返回基本都是null了

View.findViewById()和Activity.findViewById()区别的更多相关文章

  1. view和activity的区别

    activity相当于控制部分,view相当于显示部分.两者之间是多对多的关系,所有东西必须用view来显示.  viewGroup继承自view,实现了ViewManager,ViewParent接 ...

  2. view和activity的区别(转)

    activity相当于控制部分,view相当于显示部分.两者之间是多对多的关系,所有东西必须用view来显示. viewGroup继承自view,实现了ViewManager,ViewParent接口 ...

  3. Android: Custom View和include标签的区别

    Custom View, 使用的时候是这样的: <com.example.home.alltest.view.MyCustomView android:id="@+id/customV ...

  4. 关于android编程中service和activity的区别

    一. 绝大部分情况下,Service的作用是用来“执行”后台的.耗时的.重要的任务,三者缺一不可,而最重要的原因是第三点:要执行重要的任务. 因为当一个进程启动了Service后,进程的优先级变高了, ...

  5. 【android-tips】如何在view中取得activity对象

    (转载请注明出处:http://blog.csdn.net/buptgshengod) 今天想实现在view中返回上一个activity的功能,想了半天.因为在虽然view是包含于一个activity ...

  6. js架构设计模式——MVVM模式下,ViewModel和View,Model有什么区别

    MVVM模式下,ViewModel和View,Model有什么区别 Model:很简单,就是业务逻辑相关的数据对象,通常从数据库映射而来,我们可以说是与数据库对应的model. View:也很简单,就 ...

  7. inflate, findViewById与setContentView的区别与联系

    protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentV ...

  8. inflate, findViewById与setContentView的区别与联系 分类: H1_ANDROID 2014-04-18 22:54 1119人阅读 评论(0) 收藏

    protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentV ...

  9. Android View的onTouchEvent和OnTouch区别

    还是以自定义的TestButton为例. 我们可以通过重写onTouchEvent方法来处理诸如down move up的消息: public class TestButton extends But ...

随机推荐

  1. request参数获取的几种方式

    经常用到Request.QueryString[""]和Request.Form[""]来获取参数值. 今天照常用,ajax方式向后台传参,先用的Request ...

  2. free和delete把指针怎么啦?

    别看free和delete的名字恶狠狠的(尤其是delete),它们只是把指针所指的内存给释放掉,但并没有把指针本身干掉. 用调试器跟踪示例7-5,发现指针p被free以后其地址仍然不变(非NULL) ...

  3. CUDA Samples: Calculate Histogram(atomicAdd)

    以下CUDA sample是分别用C++和CUDA实现的计算一维直方图,并对其中使用到的CUDA函数进行了解说,code参考了<GPU高性能编程CUDA实战>一书的第九章,各个文件内容如下 ...

  4. matlab save 命令

    有时候要运行很长才得到结果,而这部分结果在后面修改代码之后不需要改变.可以多次利用这些结果or参数,有必要将结果保存下来. 1 save example1 A ;%A为当前环境下的变量,example ...

  5. 【剑指offer】顺时针打印矩阵,C++实现

    原创文章,转载请注明出处! 博客文章索引地址 1.题目 输入一个矩阵,按照从外向里以顺时针的顺序依次打印出每一个数字,例如,如果输入如下矩阵,则依次打印出数字1,2,3,4,8,12,16,15,14 ...

  6. JAVA多线程----用--死锁

    (1) 互斥条件:一个资源每次只能被一个进程使用.(2) 请求与保持条件:一个进程因请求资源而阻塞时,对已获得的资源保持不放.(3) 不剥夺条件:进程已获得的资源,在末使用完之前,不能强行剥夺.(4) ...

  7. 【Codeforces】Round #491 (Div. 2) 总结

    [Codeforces]Round #491 (Div. 2) 总结 这次尴尬了,D题fst,E没有做出来.... 不过还好,rating只掉了30,总体来说比较不稳,下次加油 A:If at fir ...

  8. 从hello world 说程序运行机制

    转自:http://www.cnblogs.com/yanlingyin/archive/2012/03/05/2379199.html 开篇 学习任何一门编程语言,都会从hello world 开始 ...

  9. python调用dll

    调用CALLBACK标记的dll方法要用dll = ctypes.windll.LoadLibrary( 'test.dll' ) 没有CALLBACK的方法用dll = ctypes.cdll.Lo ...

  10. python模块--logging

    一.logging模块的简单应用 import logging logging.debug('debug message') logging.info('ingo message') logging. ...