前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >多线程 以及 线程安全

多线程 以及 线程安全

作者头像
艳龙
发布2021-12-16 17:33:03
3880
发布2021-12-16 17:33:03
举报
文章被收录于专栏:yanlongli_艳龙yanlongli_艳龙

移动端开发过程中,会出现 进程线程的概念,以及多线程中 线程安全 的问题。

进程 和 线程

进程: APP 启动时,应用会启动一个新的 Linux 进程, 一个app内可以有多个进程,进程之间不共享数据。 线程: 1个进程中可以包含多个线程,线程之间数据共享。

多线程 (主线程 和 工作线程)

启动应用时,系统会为该应用创建一个称为“main”(主线程)的执行线程,在和用户交互时,主线程不允许做耗时任务,所以需要后台线程处理这些耗时任务。 这样在应用中就会存在很多的线程,也就是大家说的多线程。

多线程使用示例:

代码语言:javascript
复制
public void onClick(View v) {
    new Thread(new Runnable() {
        public void run() {
            // a potentially time consuming task
            final Bitmap bitmap =
                    processBitMap("image.png");
            imageView.post(new Runnable() {
                public void run() {
                    imageView.setImageBitmap(bitmap);
                }
            });
        }
    }).start();
}


//常用的还有使用线程池
public static final ExecutorService sTheadPoolExecutor
    = new ThreadPoolExecutor(CORE_POOL_SIZE, MAXIMUM_POOL_SIZE, KEEP_ALIVE,
    TimeUnit.SECONDS, new LinkedBlockingQueue<Runnable>(30),
            new ThreadPoolExecutor.DiscardOldestPolicy());

 private ExecutorService grayThreadPool = Executors.newSingleThreadExecutor();

线程安全

多线程之间,因为共享应用数据。所以在多个线程同时访问数据时,也就会引入线程安全的问题。

多线程安全要解决的问题是,不同线程访问同一数据时的数据安全问题。 解决线程安全的常用方法是增加 synchronized 关键字.

synchronized使用示例:

代码语言:javascript
复制
//synchronized 加在方法上
private synchronized void setNewValue(int a, int b) {
        x = a;
        y = b;
}

//synchronized 加在方法内的代码块上
private void setNewValue(int a, int b) {
    synchronized (monitor1) {
        x = a;
        y = b;
    }
}

1.synchronized保证方法内部或者代码块内部(数据)的互斥访问. 也就是同一时间,只能由1个线程来访问synchronized内的数据 2.synchronized保证线程之间对监视资源的数据同步. 也就是任何线程在获取到 Monitor 后的第⼀时 间,会先将共享内存中的数据复制到⾃自⼰己的缓存中;任何线程在释放 Monitor 的第⼀时间,会先将缓存中的数据复制到共享内存中.

线程数据同步安全中,volatile关键字也是比较常用的, volatile关键字能够保证可见性,被volatile修饰的变量,在一个线程中被改变时会立刻同步到主内存中,而另一个线程在操作这个变量时都会先从主内存更新这个变量的值 volatile使用示例:

代码语言:javascript
复制
private volatile static Singleton mSingleton = null;
private Singleton () {}

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

}

Lock / ReentrantReadWriteLock: Lock 也是给代码加锁的一种方式, 常用的ReentrantReadWriteLock可以更精细化的管理共享的内存资源。 需要特别注意的是,Lock 的加锁形式需要开发者手动释放锁

代码语言:javascript
复制
private ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
private ReentrantReadWriteLock.ReadLock readLock = lock.readLock();
private ReentrantReadWriteLock.WriteLock writeLock = lock.writeLock();

private void setValue(int newValue) {
        writeLock.lock();
        try {
            a = newValue;
        } finally {
            writeLock.unlock();
        }
    }

    private void print() {
        readLock.lock();
        try {
            System.out.println("values: " + a);
        } finally {
            readLock.unlock();
        }
    }

END!

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2020/1/15 下,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 进程 和 线程
  • 多线程 (主线程 和 工作线程)
  • 线程安全
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档