android面试录Android 面试专辑安卓开发博客

金三银四那些事(三)

2018-04-25  本文已影响69人  的一幕

说说你对android中设计模式的认识:

单例模式
这里会考到手写一个单例模式:

public class Singleton {
    private static volatile Singleton instance = null;

    private Singleton(){
    }
 
    public static Singleton getInstance() {
        if (instance == null) {
            synchronized (Singleton.class) {
                if (instance == null) {
                    instance = new Singleton();
                }
            }
        }
        return instance;
    }
}

上面有两层的非空判断,一般这里会问到,第一层是为了防止多次加锁的判断,因为同步锁是耗时的,所以只在首次为空的时候,只进行一次加锁,第二次纯粹是为了new对象的时候非空判断。

android中用到的单例模式举例:
Android-Universal-Image-Loader中的单例

private volatile static ImageLoader instance;
/** Returns singleton class instance */
public static ImageLoader getInstance() {
    if (instance == null) {
        synchronized (ImageLoader.class) {
            if (instance == null) {
                instance = new ImageLoader();
            }
        }
    }
    return instance;
}

builder模式
将一个复杂对象的构建与它的表示分离,使得同样的构建过程可以创建不同的表示

public class Person {
    private String name;
    private int age;
    private double height;
    private double weight;
    //构造函数私有化
    private Person(Builder builder) {
        this.name=builder.name;
        this.age=builder.age;
        this.height=builder.height;
        this.weight=builder.weight;
    }
    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    public double getHeight() {
        return height;
    }

    public void setHeight(double height) {
        this.height = height;
    }

    public double getWeight() {
        return weight;
    }

    public void setWeight(double weight) {
        this.weight = weight;
    }

    static class Builder{
        private String name;
        private int age;
        private double height;
        private double weight;
        public Builder name(String name){
            this.name=name;
            return this;
        }
        public Builder age(int age){
            this.age=age;
            return this;
        }
        public Builder height(double height){
            this.height=height;
            return this;
        }

        public Builder weight(double weight){
            this.weight=weight;
            return this;
        }
        //builder静态内部类里面定义一个方法来生成外部类的私有构造器
        public Person build(){
            return new Person(this);
        }
    }
}

调用部分:

Person.Builder builder=new Person.Builder();
Person person=builder
        .name("张三")
        .age(18)
        .height(178.5)
        .weight(67.4)
        .build();

android源码部分builder设计模式举例:
AlertDialog.BuilderGsonBuilder
总结:

观察者模式
定义对象间的一种一对多的依赖关系,当一个对象的状态发送改变时,所有依赖于它的对象都能得到通知并被自动更新

其实咱们在listview中刷新列表的时候,会用到adapter的notifyDataSetChanged方法,其实这里也是一个观察者模式,咱们去BaseAdapter中去找找该方法:

private final DataSetObservable mDataSetObservable = new DataSetObservable();
public void notifyDataSetChanged() {
    mDataSetObservable.notifyChanged();
}

接着看DataSetObservable中notifyChanged方法:

public void notifyChanged() {
    synchronized(mObservers) {
        // since onChanged() is implemented by the app, it could do anything, including
        // removing itself from {@link mObservers} - and that could cause problems if
        // an iterator is used on the ArrayList {@link mObservers}.
        // to avoid such problems, just march thru the list in the reverse order.
        for (int i = mObservers.size() - 1; i >= 0; i--) {
            mObservers.get(i).onChanged();
        }
    }
}

可以看到这里遍历了mObservers集合,然后调用了onChanged方法。只能去父类找找mObservers是个什么玩意。

DataSetObservable的父类.png
从这里可以看出来实际是被观察者类,其中咋们要观察的对象是DataSetObserver,也就是我们的观察者。所以说这里的观察者一旦被触发了,会调用到自己的onChanged方法。
那是什么registerDataSetObserver的呢,接着看listview的源码部分:
image.png
那看看AdapterDataSetObserver该观察者中onChange方法都做了些啥:
@Override
public void onChanged() {
     mDataChanged = true;
     mOldItemCount = mItemCount;
     mItemCount = getAdapter().getCount();

     // Detect the case where a cursor that was previously invalidated has
     // been repopulated with new data.
     if (AdapterView.this.getAdapter().hasStableIds() && mInstanceState != null
            && mOldItemCount == 0 && mItemCount > 0) {
         AdapterView.this.onRestoreInstanceState(mInstanceState);
         mInstanceState = null;
     } else {
        rememberSyncState();
     }
     checkFocus();
     requestLayout();    //onChanged的主要目的就是重布局
}

其实从最后一行调用的方法可以看出来,onChange里面做的工作就是刷新listView中整体的布局。这会知道了调用adapter.notifyDataSetChanged方法就是刷新listview列表了吧。
总结下来观察者模式实际可以用一张图说明:

观察者模型图.png

后面的原型模式策略模式请点击这里

mvc和mvp的对比:

画出mvp的umm图:

这里以登录模块为例:


mvp中登录uml图.png

说说mvvm的使用:

说说你对android中三级缓存的理解:

整个过程是先从内存缓存中找数据,如果内存缓存中没数据,到文件缓存中找,如果再没有去网络中找数据,网络中数据加载回来后,将数据保存到文件缓存中,再加载到内存中。
内存缓存:
主要用到android定义好的LruCache对象,此时需要传一个允许内存缓存的大小,一般遵循:

int maxMemory = (int) Runtime.getRuntime().maxMemory();
int cacheSize = maxMemory / 8;

这里会考到LruCache内存缓存的算法,这里的算法是最不经常使用的数据优先被移除,主要涉及到LinkedHashMap的数据结构问题。
文件缓存
这里存的时候,首先将url用MD5的encode过程,然后得到文件的name,然后通过定义的file_path目录得到File对象,得到file之后判断是不是已经存在该file的parentFile,如果不存在需要创建该file的parentFile。最后得到该file的输出流,最后使用bitmap.compress保存到本地文件中。
服务端缓存
这个就没什么好说的了,使用HttpURLConnection对象获取到bitmap的输入流,最后使用BitmapFactory.decodeStream得到bitmap对象。

说说LinkedhashMap的数据结构:

里面是一个双向链表的数据结构,维护着一个双重链接列表的顺序。此链接列表定义了迭代顺序,该迭代顺序可以是插入顺序或者是访问顺序。该迭代顺序遵循的原则如下:

java反射的机制:

HTTP网络的工作流程:

1.建立TCP连接
2.web浏览器向web服务器发送请求命令
3.web浏览器发送请求头信息
4.web服务器应答
5.web服务器发送应答头信息
6.web服务器向浏览器发送数据
7.web服务器关闭TCP连接

Http请求头都有哪些

image.png

TCP对比UDP来说都有哪些:

TCP的三次握手,四次挥手指的什么:

TCP的三次握手:

kolin学习:

说说你看过哪些框架的源码:

上一篇下一篇

猜你喜欢

热点阅读