gpt4 book ai didi

c++ - 为什么标准 :map can't accept a pointer as key-value?

转载 作者:行者123 更新时间:2023-11-28 01:39:23 27 4
gpt4 key购买 nike

我正在尝试实现一个将互斥对象放入映射中的 jni 函数。编译时,出现错误“...因为 jni 传递了一个指针”,我无法在参数中进行转换。

为什么 std:map 不能接受指针作为键值对?

给出错误的指令是这样的:

std::pair<_jobject , boost::fibers::recursive_mutex> v = 
std::pair<_jobject , boost::fibers::recursive_mutex>(*ref, *new boost::fibers::recursive_mutex());

#include <jni.h>
#include <map>
#include "ext_concurrent_fiber_FiberLock.h"
#include <boost/fiber/recursive_mutex.hpp>
std::map<_jobject, boost::fibers::recursive_mutex> mutexes;
boost::fibers::recursive_mutex lock;
// ‘std::pair<_jobject*, boost::fibers::recursive_mutex>::
//pair(_jobject&, boost::fibers::recursive_mutex&)’
// mutexes.insert(std::pair<jobject , boost::fibers::recursive_mutex>((_jobject&)ref, *new boost::fibers::recursive_mutex()));

JNIEXPORT jboolean JNICALL Java_ext_concurrent_fiber_FiberLock_setLockIfNotPresent
(JNIEnv * env, jclass clazz, jobject ref){
lock.lock();
std::map<_jobject, boost::fibers::recursive_mutex>::iterator i =mutexes.find(*ref);

if(i == mutexes.end())
{

std::pair<_jobject , boost::fibers::recursive_mutex> v
=std::pair<_jobject , boost::fibers::recursive_mutex>(*ref, *new boost::fibers::recursive_mutex());
mutexes.insert(v);
lock.unlock();
return true;
}
lock.unlock();
return false;
}

下面可以看到日志:

 jni:
[echo] Generating JNI headers
[exec] mkdir -p target/c++
[exec] g++ -c -Wall -fPIC -I/usr/lib/jvm/java-8-oracle/include/ -I/usr/lib/jvm/java-8-oracle/include/linux -I/usr/include/boost_1_66_0 -o target/c++/ext_concurrent_fiber_NativeFiber.o src/main/c++/ext_concurrent_fiber_NativeFiber.cpp
[exec] mkdir -p target/c++
[exec] g++ -c -Wall -fPIC -I/usr/lib/jvm/java-8-oracle/include/ -I/usr/lib/jvm/java-8-oracle/include/linux -I/usr/include/boost_1_66_0 -o target/c++/ext_concurrent_fiber_FiberLock.o src/main/c++/ext_concurrent_fiber_FiberLock.cpp
[exec] src/main/c++/ext_concurrent_fiber_FiberLock.cpp: In function ‘jboolean Java_ext_concurrent_fiber_FiberLock_setLockIfNotPresent(JNIEnv*, jclass, jobject)’:
[exec] src/main/c++/ext_concurrent_fiber_FiberLock.cpp:21:105: error: no matching function for call to ‘std::pair<_jobject, boost::fibers::recursive_mutex>::pair(_jobject&, boost::fibers::recursive_mutex&)’
[exec] =std::pair<_jobject , boost::fibers::recursive_mutex>(*ref, *new boost::fibers::recursive_mutex());
[exec] ^
[exec] In file included from /usr/include/c++/6/bits/stl_algobase.h:64:0,
[exec] from /usr/include/c++/6/bits/stl_tree.h:63,
[exec] from /usr/include/c++/6/map:60,
[exec] from src/main/c++/ext_concurrent_fiber_FiberLock.cpp:3:
[exec] /usr/include/c++/6/bits/stl_pair.h:423:9: note: candidate: template<class ... _Args1, long unsigned int ..._Indexes1, class ... _Args2, long unsigned int ..._Indexes2> std::pair<_T1, _T2>::pair(std::tuple<_Args1 ...>&, std::tuple<_Args2 ...>&, std::_Index_tuple<_Indexes1 ...>, std::_Index_tuple<_Indexes2 ...>)
[exec] pair(tuple<_Args1...>&, tuple<_Args2...>&,
[exec] ^~~~
[exec] /usr/include/c++/6/bits/stl_pair.h:423:9: note: template argument deduction/substitution failed:
[exec] src/main/c++/ext_concurrent_fiber_FiberLock.cpp:21:105: note: ‘_jobject’ is not derived from ‘std::tuple<_Args1 ...>’
[exec] =std::pair<_jobject , boost::fibers::recursive_mutex>(*ref, *new boost::fibers::recursive_mutex());
[exec] ^
[exec] In file included from /usr/include/c++/6/bits/stl_algobase.h:64:0,
[exec] from /usr/include/c++/6/bits/stl_tree.h:63,
[exec] from /usr/include/c++/6/map:60,
[exec] from src/main/c++/ext_concurrent_fiber_FiberLock.cpp:3:
[exec] /usr/include/c++/6/bits/stl_pair.h:356:9: note: candidate: template<class ... _Args1, class ... _Args2> std::pair<_T1, _T2>::pair(std::piecewise_construct_t, std::tuple<_Args1 ...>, std::tuple<_Args2 ...>)
[exec] pair(piecewise_construct_t, tuple<_Args1...>, tuple<_Args2...>);
[exec] ^~~~
[exec] /usr/include/c++/6/bits/stl_pair.h:356:9: note: template argument deduction/substitution failed:
[exec] src/main/c++/ext_concurrent_fiber_FiberLock.cpp:21:105: note: ‘boost::fibers::recursive_mutex’ is not derived from ‘std::tuple<_Args1 ...>’
[exec] =std::pair<_jobject , boost::fibers::recursive_mutex>(*ref, *new boost::fibers::recursive_mutex());
[exec] ^

最佳答案

您的问题与指针无关。问题是您试图存储在 map 中的对象类型不可复制,因此您不能构造它们然后将它们复制到 map 中。相反,您可以告诉 map 直接在适当的位置构建它们:

std::map<jobject, boost::fibers::recursive_mutex> mutexes;
boost::fibers::recursive_mutex lock;

JNIEXPORT jboolean JNICALL
Java_ext_concurrent_fiber_FiberLock_setLockIfNotPresent(JNIEnv* env, jclass clazz, jobject ref)
{
std::lock_guard<boost::fibers::recursive_mutex> lck(lock);

auto i = mutexes.find(ref);
if(i == mutexes.end())
{
mutexes.emplace(std::piecewise_construct,
std::forward_as_tuple(ref),
std::tuple<>{});
return true;
}
return false;
}

在这里,我使用了 std::map::emplace连同 std::pairstd::piecewise_construct constructor告诉 map 在适当的位置构建它的元素。这样,就不需要将互斥体复制到 map 中。

关于c++ - 为什么标准 :map can't accept a pointer as key-value?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47955869/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com