这是B+树的一个节点。我想使用智能指针,因为我的程序泄漏了大量内存。如何使用智能指针转换代码?
class node
{
public:
long* key;
int capacity;
node** nodes;
node* parent;
long* value;
node ( int order ) {
key = new long[order + 1];
value = new long[order + 1];
nodes = new node *[order + 2];
capacity = 0;
parent = NULL;
for ( int i = 0; i <= order + 1; i++ ) {
this->nodes[i] = NULL;
}
}
~node() {
delete[] key;
delete[] value;
for ( int i = 0; i <= order …Run Code Online (Sandbox Code Playgroud) 毫无疑问,共享指针是个好主意。但是,只要大型程序包含原始指针,我认为使用共享指针就有很大的风险。主要是,您将失去对指向包含原始指针的对象的指针的实际生命周期的控制,并且错误将发生在难以查找和调试的位置。
所以我的问题是,是否有尝试不向现代C ++添加不依赖于使用共享指针的“弱指针”?我的意思是仅当指针在程序的任何部分删除时,该指针将变为NULL。是否有理由不使用这种自制包装纸?
为了更好地解释我的意思,以下是我所做的“弱指针”。我将其命名为WatchedPtr。
#include <memory>
#include <iostream>
template <typename T>
class WatchedPtr {
public:
// the only way to allocate new pointer
template <typename... ARGS>
WatchedPtr(ARGS... args) : _ptr (new T(args...)), _allocated (std::make_shared<bool>(true)) {}
WatchedPtr(const WatchedPtr<T>& other) : _ptr (other._ptr), _allocated (other._allocated) {}
// delete the pointer
void del () {delete _ptr; *_allocated = false;}
auto& operator=(const WatchedPtr<T> &other) { return *this = other; }
bool isNull() const { return *_allocated; }
T* operator->() const { return _ptr; } …Run Code Online (Sandbox Code Playgroud) 我在Qt工作,我没有提到它,因为我认为这只是C++问题。
我用共享指针解决了这个问题,所以不要给我解决方案。但这是理解的问题,我想了解为什么它不起作用。
我正在尝试以下操作:
测试.h:
#include <QObject>
#include "response.h"
#include <memory>
class Test : public QObject
{
Q_OBJECT
public:
explicit Test(QObject *parent = nullptr);
signals:
void signal(std::unique_ptr<Response> resp);
public slots:
};
Run Code Online (Sandbox Code Playgroud)
测试.cpp:
Test::Test(QObject *parent) : QObject(parent)
{
std::unique_ptr<Response> response(new Response(5));
emit signal(std::move(response));
}
Run Code Online (Sandbox Code Playgroud)
Response 班级:
class Response
{
public:
Response(int data);
private:
int data;
};
Run Code Online (Sandbox Code Playgroud)
我知道std::unique_ptr不能复制,我std::move在这里使用。但尽管如此,我还是收到了一个错误:
moc_test.cpp:75:85: error: use of deleted function ‘std::unique_ptr<_Tp, _Dp>::unique_ptr(const std::unique_ptr<_Tp, _Dp>&) [with _Tp = Response; _Dp = std::default_delete<Response>]’
case 0: _t->signal((*reinterpret_cast< std::unique_ptr<Response>(*)>(_a[1]))); …Run Code Online (Sandbox Code Playgroud) 对于C ++,有一个类似的,非常受欢迎的问题,但对于Rust,我找不到类似的现有问题。
那么,什么是用例Box,Rc,Ref,RefMut(其他人?)拉斯特?
这个问题的重要部分(对我个人而言):什么时候应该使用智能指针代替引用?
我知道《锈皮书》非常非常彻底地解释了它,但我希望在主题上有一个简洁明了的“备忘单”,其中可能包含本书中缺少的一些实际示例。
这是关于智能指针(例如唯一指针)的一个很好的答案:什么是智能指针,我应该何时使用?.
这是他们提供的一个示例,作为唯一指针的最简单用法:
void f()
{
{
std::unique_ptr<MyObject> ptr(new MyObject(my_constructor_param));
ptr->DoSomethingUseful();
} // ptr goes out of scope --
// the MyObject is automatically destroyed.
// ptr->Oops(); // Compile error: "ptr" not defined
// since it is no longer in scope.
}
Run Code Online (Sandbox Code Playgroud)
然而,这引出了一个问题:在这种情况下,目标是简单地删除对象(释放内存),当它超出范围时,唯一指针指向,为什么不把整个对象放在堆栈上呢? , 像这样??
void f()
{
{
MyObject myobj(my_constructor_param);
myobj.DoSomethingUseful();
} // myobj goes out of scope --
// and is automatically destroyed.
// myobj.Oops(); // Compile error: "myobj" not defined
// since it is no longer …Run Code Online (Sandbox Code Playgroud) 在下面的 C++ 调用 reset() 列表、向量、映射中,既没有错误也没有警告。
但是,当我尝试在 set 中执行此操作时,出现错误。
错误消息是 [ 没有匹配的成员函数调用 'reset' ]
为什么会这样???有人可以与社区分享您的知识吗?
std::shared_ptr<int> sp;
sp.reset(new int(11));
sp.reset();
std::map<int, std::shared_ptr<int>> my_map;
for (auto it = my_map.begin(); it != my_map.end(); ++it) {
it->second.reset();
(*it).second.reset();
}
std::list<std::shared_ptr<int>> my_list;
for (auto& x : my_list) {
x.reset();
}
std::vector<std::shared_ptr<int>> my_vec;
for (auto it = my_vec.begin(); it != my_vec.end(); ++it) {
it->reset();
(*it).reset();
}
std::set<std::shared_ptr<int>> my_set;
for (auto& x : my_set) {
x.reset(); // ERROR!!!
}
for (auto it = my_set.begin(); it != my_set.end(); …Run Code Online (Sandbox Code Playgroud) 据我所知,取消引用 -*smart_ptr和get()+ 取消引用*smart_ptr.get()使用智能指针做同样的事情,但可能有一些我不知道的事情,因为我在第二种方法中看到了很多情况被使用了,那有什么意义呢?它会以任何方式影响性能吗?
我正在用 C++ 制作一些 SDL2 包装器。像这样:
/* header file */
#include <SDL_mixer.h>
#include <memory>
class SDL2_Music {
public:
~SDL2_Music() { free(); }
bool loadMusic(const std::string& path);
bool play(int loops = -1);
// more methods
private:
void free();
Mix_Music* music_ = nullptr;
};
/* cpp file */
void SDL2_Music::free() {
if (music_ != nullptr) {
Mix_FreeMusic(music_);
music_ = nullptr;
}
}
bool SDL2_Music::loadMusic(const std::string& path) {
free();
music_ = Mix_LoadMUS(path.c_str()); // this returns a Mix_Music*
if (music_ == nullptr) {
ktp::logSDLError("Mix_LoadMUS");
return …Run Code Online (Sandbox Code Playgroud) 下面的代码给出了错误:Call to deleted constructor of 'std::unique_ptr<int>' 'unique_ptr' has been explicitly marked deleted here passing argument to parameter 'item' here。
有人可以解释一下这是为什么吗?我本以为一切都会好起来的,因为我std::move在调用foo.add.
#include <iostream>
#include <memory>
#include <set>
class Foo {
public:
void add(std::unique_ptr<int> item) {
set.emplace(std::move(item));
}
private:
std::set<std::unique_ptr<int>> set;
};
int main() {
Foo foo;
std::set<std::unique_ptr<int>> set;
set.emplace(std::make_unique<int>(1));
set.emplace(std::make_unique<int>(2));
set.emplace(std::make_unique<int>(3));
for (auto &item : set) {
foo.add(std::move(item)); // error on this line
}
return 0;
}
Run Code Online (Sandbox Code Playgroud) 我在 main.cpp 中有一个例程,用户将在其中指定要在程序中执行的模式。一旦指定了模式,就会执行相应的块——首先将父求解器向下转换为子求解器,并调用solve子类中的关联方法。
std::unique_ptr<SudokuSolver> solver;
if (mode == MODES::SEQUENTIAL_BACKTRACKING)
{
solver = std::make_unique<SudokuSolver_SequentialBacktracking>();
SudokuSolver_SequentialBacktracking* child_solver = dynamic_cast<SudokuSolver_SequentialBacktracking*>(solver.get());
child_solver->solve(board);
}
else if (mode == MODES::SEQUENTIAL_BRUTEFORCE)
{
solver = std::make_unique<SudokuSolver_SequentialBruteForce>();
SudokuSolver_SequentialBruteForce* child_solver = dynamic_cast<SudokuSolver_SequentialBruteForce*>(solver.get());
child_solver->solve(board);
}
else if (mode == MODES::PARALLEL_BRUTEFORCE)
{
int NUM_THREADS = (argc >= 5) ? std::stoi(argv[4]) : 2;
omp_set_num_threads(NUM_THREADS);
#pragma omp parallel
{
#pragma omp single nowait
{
solver = std::make_unique<SudokuSolver_ParallelBruteForce>();
SudokuSolver_ParallelBruteForce* child_solver = dynamic_cast<SudokuSolver_ParallelBruteForce*>(solver.get());
child_solver->solve(board);
}
}
}
else if (mode == MODES::SEQUENTIAL_DANCINGLINKS)
{
solver …Run Code Online (Sandbox Code Playgroud) smart-pointers ×10
c++ ×9
c++11 ×4
unique-ptr ×2
b-tree ×1
c++17 ×1
heap-memory ×1
move ×1
pointers ×1
qmetaobject ×1
qt ×1
rust ×1
sdl-2 ×1
set ×1
shared-ptr ×1
stack ×1
std ×1
stdset ×1
templates ×1