首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

有没有更好的方法来确定computeIfAbsent是否返回了一个新值?

在Java中,我们可以使用computeIfAbsent方法来在Map中根据指定的键获取对应的值,如果该键不存在,则会根据提供的函数生成一个新值并将其放入Map中。但是,我们如何确定computeIfAbsent是否返回了一个新值呢?

一种方法是使用一个辅助变量来判断是否返回了新值。我们可以在computeIfAbsent方法调用之前先获取Map中对应键的值,并将其保存在一个变量中。然后,在computeIfAbsent方法调用之后,再次获取该键的值,并与之前保存的值进行比较。如果两个值相等,则说明computeIfAbsent没有生成新值;如果两个值不相等,则说明computeIfAbsent生成了一个新值。

另一种方法是使用原子变量来判断是否返回了新值。我们可以使用AtomicReference类来保存Map中对应键的值。在computeIfAbsent方法调用之前,我们可以使用get方法获取并保存原始值。然后,在computeIfAbsent方法调用之后,我们可以使用compareAndSet方法将原始值与新值进行比较。如果compareAndSet返回true,则说明computeIfAbsent生成了一个新值;如果返回false,则说明computeIfAbsent没有生成新值。

这些方法可以帮助我们确定computeIfAbsent是否返回了一个新值,从而更好地控制程序的逻辑和流程。

参考链接:

  • computeIfAbsent方法文档:https://docs.oracle.com/javase/8/docs/api/java/util/Map.html#computeIfAbsent-K-java.util.function.Function-
页面内容是否对你有帮助?
有帮助
没帮助

相关·内容

【Java 基础篇】深入理解Java HashMap:使用注意事项和性能优化

判断是否包含键或 您可以使用containsKey方法来检查HashMap是否包含特定键: boolean containsKey = hashMap.containsKey("apple"); //...); 这将创建一个与hashMap相同HashMap。...您可以使用computeIfAbsent方法来实现这一点: hashMap.computeIfAbsent("orange", key -> { // 在键"orange"不存在时,执行此操作并返回默认...这些是一些更多操作HashMap方法和概念,它们可以帮助您更好地使用和管理HashMap集合。根据您需求,选择适当方法来操作和处理HashMap中数据。...如果尝试将相同键插入HashMap中,将覆盖旧可以重复: HashMap中可以重复。多个键可以映射到相同

1.6K40
  • Lambda表达式你会用吗?

    函数式编程就是一种抽象程度很高编程范式,纯粹函数式编程语言编写函数没有变量,因此,任意一个函数,只要输入是确定,输出就是确定,这种纯函数我们称之为没有副作用。...可选返回关键字:如果主体只有一个表达式返回则编译器会自动返回,大括号需要指定明表达式返回了一个数值。 // 1. 不需要参数,返回为 5 () -> 5 // 2....批量迭代可以降低迭代开销。 Spliterator是可拆分一个Spliterator可以通过调用Spliterator trySplit()方法来尝试分成两个。...一个是this,另一个返回那个,这两个迭代器代表元素没有重叠。 可通过(多次)调用Spliterator.trySplit()方法来分解负载,以便多线程处理。...Function是一个函数接口,里面有一个待实现方法R apply(T t). computeIfAbsent()常用来对Map某个key建立初始化映射.比如我们要实现一个多值映射,Map定义可能是

    90230

    Redis如何删除数量过万以上Key而不影响业务

    那大家会问,有没有更好方法来解决这个问题?答案是当然用,请接着看下文。...命令是一个基于游标的迭代器,SCAN命令每次被调用之后,都会向用户返回一个游标,用户在下次迭代时需要使用这个游标作为SCAN命令游标参数,以此来延续之前迭代过程,直到服务器向用户返回为0游标时...上面这个例子意思是扫描所有前缀为testkey-key。第一次迭代使用0作为游标,表示开始一次迭代,同时使用了MATCH匹配前缀为testkey-key,返回了游标值34以及遍历到数据。...当SCAN命令游标参数被设置为0时,服务器将开始一次迭代,而当redis服务器向用户返回为0游标时,表示迭代已结束,这是唯一迭代结束判定方式,而不能通过返回结果集是否为空判断迭代结束。...遍历过程中如果有数据修改,改动后数据能不能遍历到是不确定。 单次返回结果是空并不意味着遍历结束,而要看返回游标值是否为零。

    4.4K30

    「硬核JS」图解Promise迷惑行为|运行机制补充

    then方法返回来生成 Promise 对象,这块逻辑复杂些,规范中可以抽离出一个方法来做这件事,我们来照做。.../** * 解析then返回Promise对象 * @param {Object} Promise对象,就是我们创建promise2实例 * @param {*} x 上一个then返回...哦,原来 then 方法并不是在上一个 Promise 对象 resolve 后才执行,它在一开始就执行并返回了一个 Promise,在返回 Promise 中会根据上一个 Promise 状态来做判断...,和直接 return 一个一样,都会在上一个 Promise 状态为成功态时调用其返回时内部创建 Promise resolve 方法并将传出。...我们之前手写实现,当使用 Promise 返回一个 Promise 时,内部会调用它 then 方法从而产生一个微任务,其回调入队,后面微任务队列执行到这个回调时,拿到传入作处理后再 resolve

    2.2K30

    Java延迟加载最佳实践应用示例!

    总体而言,使用Eager方式让编码本身更加简单,然而使用Lazy方式通常而言,即意味着更好效率。...                return heavyInstance;              }          }                  //第一次调用方法来会将heavy重定向到...在方法体中会首先判断当前heavy是否是HeavyInstance一个实例。如果不是,就会将heavy对象替换成HeavyFactory类型实例。...int number) {         return number > 1 &&             // 依次从2到number平方根判断number是否可以整除该,即divisor             ...,则直接返回该             return number + 1;         else // 否则继续从下一个数据后面继续找到第一个素数返回,递归             return

    74120

    面霸篇:Java 核心集合容器全解(核心卷二)

    集合特点 对象封装数据,多个对象需要用集合存储; 对象个数可以确定使用数组更高效,不确定个数情况下可以使用集合,因为集合是可变长度。 集合与数组区别 数组是固定长度;集合可变长度。...在读操作时不加锁,跟 ArrayList 类似;在写操作时,复制出一个数组,在数组上进行操作,操作完了,将底层数组指针指向数组。 适合使用在读多写少场景。...==指引用是否相同, equals() 指的是是否相同。...用户自定义 Key 类最佳实践是使之为不可变,这样 hashCode() 可以被缓存起来,拥有更好性能。...正确写法: //利用computeIfAbsent()方法来实例化LongAdder,然后利用LongAdder来进行线程安全计数 freqs.computeIfAbsent(key, k -> new

    37021

    Java 并发之线程池学习

    milliseconds,runnableTaskQueue, threadFactory,handler); 参数说明: corePoolSize 线程池中任务基本个数 提交一个任务时,若线程池中个数未达到基本个数...,则新建一个线程 到线程池中线程数达到基本个数时,再提交任务,则看是否有空闲线程,有则只直接使用 若无空闲线程,则几条任务放入排队 maximumPoolSize 线程chi池中任务做多个数...Future 对象,通过调用future.get() 可以获取线程返回,其中这个方程是线程阻塞,直到返回了结果之后,才会继续执行下去 关闭线程 线程池shutdown或shutdownNow...方法来关闭线程池 shutdown原理是只是将线程池状态设置成SHUTDOWN状态,然后中断所有没有正在执行任务线程 shutdownNow原理是遍历线程池中工作线程,然后逐个调用线程interrupt...方法来中断线程,所以无法响应中断任务可能永远无法终止 调用了这两个关闭方法其中一个,isShutdown方法就会返回true。

    614100

    不就是书上 5.6 小节吗?

    看到这个问题瞬间,不知道你脑袋里面有没有电光火石般想起缓存问题三连击:缓存雪崩、缓存击穿、缓存穿透。 毕竟应对缓存击穿解决方案之一就是只需要一个请求线程去做构建缓存,其他线程就轮询等着。...所以,我们接着就要关注一下 ConcurrentHashMap 这个方法是怎么搞得了: 还是通过 synchronized 方法来保证了原子性,当操作是同一个 key 时候保证只有一个线程去执行...extends V> mappingFunction) computeIfAbsent,首先它也是一个线程安全方法,这个方法会检查 Map 中 Key,如果发现 Key 不存在或者对应是 null...,则调用 Function 来产生一个,然后将其放入 Map,最后返回这个;否则的话返回 Map 已经存在。...但是从程序实现优雅角度来说,还是 putIfAbsent 方法更好。 坑怎么办? 前面不是说最终方案有两个坑嘛: 一个是不支持缓存过期机制。 一个是不支持缓存淘汰机制。

    20610

    快来学这几个“”方法

    图片getOrDefault这个方法名很直观,见名知意:尝试获取key对应,如果未获取到,就返回默认。...看一个使用例子,写法会比老写法更加简洁:private static void testGetOrDefault() { Map map = new HashMap...我们要实现逻辑是,遍历List中每个元素,如果这个元素在Map中存在,Map中+1;如果不存在,则放入Map中,次数()为1。...putIfAbsent也是一个见名知意方法:不存在key或者为null时,才将键值对放入Map。跟put方法相比,这个方法不会直接覆盖已有的,在不允许覆盖旧场景使用起来会比较简洁。...,让我想起一张远古图不过在不同场景使用不同方法,尽量把代码写简洁和优雅,才是一个程序猿不断追求目标吧。

    6310

    别再这么写代码了,这几个方法不香吗?

    不过最近 Review 项目代码时候发现,虽然很多项目工程已经使用了 JDK8,但是工程代码却很少使用到 JDK8 特性、新方法。...所以针对这种情况,其实可以使用条件运算符,设置一个默认空,从而避免后续处理发生空指针。...MapUtils.getString(pojo.getMap(),"支付", ""); 巧用 computeIfAbsent 日常开发中,我们会碰到这类场景,需要一个键需要映射到多个,这个时候我们可以使用...而 computeIfAbsent将会返回 mappingFunction计算之后,像上面的场景直接返回就是 new ArrayList。 这一点需要注意一下,切勿用错方法,导致空指针。...最后针对上面这种一个键需要映射到多个,其实还有一个更优秀解决办法,使用 Google Guava 提供集合类型 Multiset,以此快速完成一个键需要映射到多个场景。

    85121

    ConcurrentHashMap里面也有死循环,作者留“彩蛋”?

    接着调用 computeIfAbsent 方法,获取到 null 后调用 getValue 方法,将该方法返回和当前 key 关联起来。 所以,第二次获取时候拿到了 “why技术”。...但是目前而言,这种机制就算做出来,工作效率也是非常低下,比如在当前这个案例下。但是现在我们至少清楚知道,是否要实现这种机制是不能确定。...问题在于我们在进行 computeIfAbsent 时候,里面还有一个 computeIfAbsent。...现在 “AaAa” 就等着这个 computeIfAbsent 操作返回,然后进行下一步操作,也就是进行标号为 ③ 操作了。 接着 “BBBB” 就来了。 ?...接下来到标号为 ③ 地方,里面有一个 MOVED,这个 MOVED 是干啥呢? ? 表示当前 ConcurrentHashMap 是否是在进行扩容。

    37631

    干货 | Java8 特性指导手册

    Sorted 排序 Sorted 同样是一个中间操作,它参是一个 Stream 流。另外,我们可以传入一个 Comparator 用来自定义排序,如果不传,则使用默认排序规则。...Match 匹配 顾名思义, match 用来做匹配操作,它返回一个 boolean 类型。通过 match, 我们可以方便验证一个 list 中是否存在某个类型元素。...: // computeIfPresent(), 当 key 存在时,才会做相关处理 // 如下:对 key 为 3 ,内部会先判断是否存在,存在,则做 value + key 拼接操作 map.computeIfPresent.../ 如下:先判断 key 为 23 元素是否存在,不存在,则添加 map.computeIfAbsent(23, num -> "val" + num); map.containsKey(23);...// true // 先判断 key 为 3 元素是否存在,存在,则不做任何处理 map.computeIfAbsent(3, num -> "bam"); map.get(3);

    1.3K20

    面试阿里被P8质问:ConcurrentHashMap真的线程安全吗?

    显然,利用size方法计算差异,是一个流程控制 诸如putAll这样聚合方法也不能确保原子性,在putAll过程中去获取数据可能会获取到部分数据 2.3 解决方案 整段逻辑加锁: [em987s6z7r.png...这就引申出代码中常见一个问题:在使用一些类库提供高级工具类时,开发人员可能还是按照旧方式去使用这些类,因为没有使用其真实特性,所以无法发挥其威力。...性能,优化后: [45niism1jb.png] ConcurrentHashMap原子性方法computeIfAbsent做复合逻辑操作,判断K是否存在V,若不存在,则把Lambda运行后结果存入...Map作为V,即新创建一个LongAdder对象,最后返回V 因为computeIfAbsent返回V是LongAdder,是个线程安全累加器,可直接调用其increment累加。...不存在时候,putIfAbsent返回null,小心空指针,而computeIfAbsent返回计算后 当Key不存在时候,putIfAbsent允许put null进去,而computeIfAbsent

    1.2K32

    ConcurrentHashMap里面也有死循环,作者留下“彩蛋”了解一下?

    接着调用 computeIfAbsent 方法,获取到 null 后调用 getValue 方法,将该方法返回和当前 key 关联起来。 所以,第二次获取时候拿到了 “why技术”。...但是目前而言,这种机制就算做出来,工作效率也是非常低下,比如在当前这个案例下。但是现在我们至少清楚知道,是否要实现这种机制是不能确定。...Bug 原因 导致这个 Bug 原因也是一句话就能说清楚,前面的 Pardeep 老哥也说了: 问题在于我们在进行 computeIfAbsent 时候,里面还有一个 computeIfAbsent...现在 “AaAa” 就等着这个 computeIfAbsent 操作返回,然后进行下一步操作,也就是进行标号为 ③ 操作了。 接着 “BBBB” 就来了。...标号为 ⑦ 地方,判断 f 节点是否是红黑树存储。当然不是的。所以,不会进入这个分支。 标号为 ⑧ 地方,binCount 代表是该下标里面,有几个 node 节点。很明显,现在一个都没有。

    1.3K00

    【小家java】Java中集合List、Set、Map删除元素方法大总结(避免ConcurrentModificationException异常)

    因此我们平时使用中少不了对List增删改查,本文就针对于对List“删”操作进行一个分析,顺便说几个坑,希望能帮助到大家以后可以避免踩坑 2、栗子 有一个List,如果我们要删除其中一个元素,怎么办呢...,是不是以后我们以后就可以用这种方法来删除了呢?...map.put("1", 2)); //null 如果是添加成功,返回null System.out.println(map.put("1", 3)); //2 如果已经存在此key了 会用覆盖旧...返回 public static void main(String[] args) { Map map = new HashMap();...可以这样写 这样若已存在,返回oldValue,若不存在就执行计算,也是返回一个可用List // 这样对null非常友好,特别好用~~~~~~~~~~ list

    2K30

    Map在Java 8中增加非常实用哪些函数接口?

    使用该方法程序员可以省去查询指定键值是否存在麻烦....V value)方法实现,该方法总是会用替换原来.为了更精确控制替换行为,Java8在Map中加入了两个replace()方法,分别如下: replace(K key, V value),只有在当前...参数中BiFunction函数接口前面已经介绍过,里面有一个待实现方法R apply(T t, U u). merge()方法虽然语义有些复杂,但该方法用方式很明确,一个比较常见场景是将错误信息拼接到原来信息上...Function是一个函数接口,里面有一个待实现方法R apply(T t). computeIfAbsent()常用来对Map某个key建立初始化映射.比如我们要实现一个多值映射,Map定义可能是...Map,要向Map中放入,可通过如下代码实现: Map> map = new HashMap(); // Java7及以前实现方式 if

    2K50
    领券