当前位置: 首页 > news >正文

Collections.unmodifiableList

Collections.unmodifiableList 是 Java Collections Framework 提供的一个方法,用于创建一个不可修改的视图(unmodifiable view)列表。这个方法返回的列表是对原始列表的一个包装,任何对这个包装列表的修改操作都会抛出 UnsupportedOperationException

使用场景

  • 防止修改:当你希望一个列表在某个范围内不可修改时,可以使用 Collections.unmodifiableList 来创建一个不可修改的视图。
  • 安全性:在方法返回一个列表时,使用不可修改的视图可以防止调用者修改原始列表,从而提高代码的安全性和稳定性。

示例代码

以下是如何使用 Collections.unmodifiableList 的示例:

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;public class UnmodifiableListExample {public static void main(String[] args) {// 创建一个可修改的列表List<String> modifiableList = new ArrayList<>();modifiableList.add("Apple");modifiableList.add("Banana");modifiableList.add("Cherry");// 创建一个不可修改的视图列表List<String> unmodifiableList = Collections.unmodifiableList(modifiableList);// 输出不可修改的列表System.out.println("Unmodifiable List: " + unmodifiableList);// 尝试修改不可修改的列表(会抛出 UnsupportedOperationException)try {unmodifiableList.add("Date");} catch (UnsupportedOperationException e) {System.out.println("Cannot modify unmodifiable list: " + e.getMessage());}// 修改原始列表modifiableList.add("Date");// 输出不可修改的列表(会反映原始列表的修改)System.out.println("Unmodifiable List after modifying original list: " + unmodifiableList);}
}

解释

  1. 创建可修改的列表:首先创建一个 ArrayList,并添加一些元素。
  2. 创建不可修改的视图列表:使用 Collections.unmodifiableList 方法创建一个不可修改的视图列表。
  3. 尝试修改不可修改的列表:尝试对不可修改的列表进行添加操作,会抛出 UnsupportedOperationException
  4. 修改原始列表:修改原始列表后,不可修改的视图列表会反映这些修改,因为它只是对原始列表的一个包装。

注意事项

  • 不可修改的视图Collections.unmodifiableList 返回的列表只是一个视图,原始列表的修改会反映到这个视图中。
  • 线程安全Collections.unmodifiableList 并不保证线程安全。如果需要线程安全的不可修改列表,可以使用 Collections.synchronizedListCollections.unmodifiableList 结合使用。

线程安全示例

如果需要线程安全的不可修改列表,可以这样做:

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;public class ThreadSafeUnmodifiableListExample {public static void main(String[] args) {// 创建一个线程安全的可修改列表List<String> synchronizedList = Collections.synchronizedList(new ArrayList<>());synchronizedList.add("Apple");synchronizedList.add("Banana");synchronizedList.add("Cherry");// 创建一个不可修改的视图列表List<String> unmodifiableList = Collections.unmodifiableList(synchronizedList);// 输出不可修改的列表System.out.println("Unmodifiable List: " + unmodifiableList);// 尝试修改不可修改的列表(会抛出 UnsupportedOperationException)try {unmodifiableList.add("Date");} catch (UnsupportedOperationException e) {System.out.println("Cannot modify unmodifiable list: " + e.getMessage());}// 修改原始列表synchronizedList.add("Date");// 输出不可修改的列表(会反映原始列表的修改)System.out.println("Unmodifiable List after modifying original list: " + unmodifiableList);}
}

通过这种方式,可以确保列表在多线程环境下的安全性,同时防止对列表的修改。

List的拷贝

在 Java 中,有多种方法可以复制一个 List。以下是一些常见的方法:

1. 使用 ArrayList 构造函数

你可以使用 ArrayList 的构造函数来创建一个新的 ArrayList,并将原始列表的元素复制到新的列表中。

import java.util.ArrayList;
import java.util.List;public class ListCopyExample {public static void main(String[] args) {List<String> originalList = new ArrayList<>();originalList.add("Apple");originalList.add("Banana");originalList.add("Cherry");// 使用 ArrayList 构造函数复制列表List<String> copiedList = new ArrayList<>(originalList);// 输出复制的列表System.out.println("Copied List: " + copiedList);}
}

2. 使用 Collections.copy

Collections.copy 方法可以将一个列表的内容复制到另一个列表中。需要注意的是,目标列表必须有足够的空间来容纳源列表的所有元素。

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;public class ListCopyExample {public static void main(String[] args) {List<String> originalList = new ArrayList<>();originalList.add("Apple");originalList.add("Banana");originalList.add("Cherry");// 创建一个大小相同的目标列表List<String> copiedList = new ArrayList<>(Collections.nCopies(originalList.size(), (String) null));// 使用 Collections.copy 复制列表Collections.copy(copiedList, originalList);// 输出复制的列表System.out.println("Copied List: " + copiedList);}
}

3. 使用 addAll 方法

你可以使用 addAll 方法将一个列表的所有元素添加到另一个列表中。

import java.util.ArrayList;
import java.util.List;public class ListCopyExample {public static void main(String[] args) {List<String> originalList = new ArrayList<>();originalList.add("Apple");originalList.add("Banana");originalList.add("Cherry");// 创建一个新的列表List<String> copiedList = new ArrayList<>();// 使用 addAll 方法复制列表copiedList.addAll(originalList);// 输出复制的列表System.out.println("Copied List: " + copiedList);}
}

4. 使用 streamCollectors.toList

你可以使用 Java 8 的 stream API 和 Collectors.toList 方法来复制一个列表。

import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;public class ListCopyExample {public static void main(String[] args) {List<String> originalList = new ArrayList<>();originalList.add("Apple");originalList.add("Banana");originalList.add("Cherry");// 使用 stream 和 Collectors.toList 复制列表List<String> copiedList = originalList.stream().collect(Collectors.toList());// 输出复制的列表System.out.println("Copied List: " + copiedList);}
}

5. 使用 clone 方法(适用于 ArrayList

如果你使用的是 ArrayList,可以直接使用其 clone 方法来复制列表。

import java.util.ArrayList;
import java.util.List;public class ListCopyExample {public static void main(String[] args) {List<String> originalList = new ArrayList<>();originalList.add("Apple");originalList.add("Banana");originalList.add("Cherry");// 使用 clone 方法复制列表List<String> copiedList = (List<String>) ((ArrayList<String>) originalList).clone();// 输出复制的列表System.out.println("Copied List: " + copiedList);}
}

总结

以上方法都可以用来复制一个 List,具体选择哪种方法取决于你的需求和使用场景。如果你需要一个简单的、快速的复制,可以使用 ArrayList 构造函数或 addAll 方法。如果你需要更灵活的操作,可以考虑使用 streamCollectors.toList

相关文章:

  • 【Vue】Vue3 安装 Tailwind CSS 入门
  • Golang | Leetcode Golang题解之第240题搜索二维矩阵II
  • vue2导入elementui组件库
  • LabVIEW电路产品功能自动检测系统
  • 目标检测入门:4.目标检测中的一阶段模型和两阶段模型
  • 【ELK+Kafka+filebeat分布式日志收集】分布式日志收集详解
  • Flutter 状态管理新境界:多Provider并行驱动UI
  • 快捷:通过胶水语言实现工作中测试流程并行、加速
  • nginx全局块的user指令
  • 基于 Vue 3 和 Element Plus 构建图书管理系统
  • 计算机毕业设计Python深度学习游戏推荐系统 Django PySpark游戏可视化 游戏数据分析 游戏爬虫 Scrapy 机器学习 人工智能 大数据毕设
  • Airdrop 2049 第二季如何捕捉全新机遇?专家大咖带你揭秘!
  • B树:深入解析与实战应用
  • 华为的热机备份和流量限制
  • 纯净IP的判断标准及代理深度分析
  • Cookie 在前端中的实践
  • cookie和session
  • Debian下无root权限使用Python访问Oracle
  • ERLANG 网工修炼笔记 ---- UDP
  • ESLint简单操作
  • go语言学习初探(一)
  • JavaScript服务器推送技术之 WebSocket
  • Java-详解HashMap
  • java小心机(3)| 浅析finalize()
  • Phpstorm怎样批量删除空行?
  • React-生命周期杂记
  • Shadow DOM 内部构造及如何构建独立组件
  • Theano - 导数
  • vue.js框架原理浅析
  • 将回调地狱按在地上摩擦的Promise
  • 聊一聊前端的监控
  • 视频flv转mp4最快的几种方法(就是不用格式工厂)
  • 异步
  • 原创:新手布局福音!微信小程序使用flex的一些基础样式属性(一)
  • No resource identifier found for attribute,RxJava之zip操作符
  • CMake 入门1/5:基于阿里云 ECS搭建体验环境
  • elasticsearch-head插件安装
  • 分布式关系型数据库服务 DRDS 支持显示的 Prepare 及逻辑库锁功能等多项能力 ...
  • # AI产品经理的自我修养:既懂用户,更懂技术!
  • #define用法
  • #Linux(Source Insight安装及工程建立)
  • #stm32整理(一)flash读写
  • #我与Java虚拟机的故事#连载18:JAVA成长之路
  • (Redis使用系列) SpirngBoot中关于Redis的值的各种方式的存储与取出 三
  • (分布式缓存)Redis哨兵
  • (附源码)apringboot计算机专业大学生就业指南 毕业设计061355
  • (附源码)springboot宠物医疗服务网站 毕业设计688413
  • (论文阅读40-45)图像描述1
  • (学习日记)2024.01.19
  • .360、.halo勒索病毒的最新威胁:如何恢复您的数据?
  • .NET 8 跨平台高性能边缘采集网关
  • .NET I/O 学习笔记:对文件和目录进行解压缩操作
  • .net6解除文件上传限制。Multipart body length limit 16384 exceeded
  • .Net多线程总结
  • .NET中使用Protobuffer 实现序列化和反序列化