我正在尝试实现类似绘画的绘图程序。我有两个std :: list,其中包含对形状的shared_ptrs。一个是“撤销”链接列表,另一个是“重做”。在我对Shape shared_ptr调用reset之前,通过push_back将shared_ptr添加到撤消链接列表。
LRESULT CDrawView::OnLButtonUp(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled)
{
int xPos= GET_X_LPARAM(lParam);
int yPos = GET_Y_LPARAM(lParam);
end.X = xPos;
end.Y = yPos;
m_shape->setEnd(xPos,yPos);
m_shape->Draw(m_GraphicsImage);
Undo.push_back(m_shape);
RedrawWindow();
return 0;
}
当给出撤消命令时,我抓住撤消链接列表后面的shared_ptr并将其移动到重做链表。然后,将m_GraphicsImage清除为白色,最后尝试通过撤消列表,重新绘制所有内容。
LRESULT CMainFrame::OnUndo(WORD /*wNotifyCode*/, WORD /*wID*/, HWND /*hWndCtl*/, BOOL& /*bHandled*/)
{
m_view.Redo.push_back(m_view.Undo.back()); //gets the first element that was Undo
m_view.m_GraphicsImage.Clear(255); //Clears the board
for(std::list<std::shared_ptr<Shape>>::iterator it = m_view.Undo.end(); it!=m_view.Undo.begin() ; it--)
{
it->get()->Draw(m_view.m_GraphicsImage);
}
return 0;
}
我一直得到列表迭代器而不是deferencable ....我只是想创建一个简单的撤消和重做
答案 0 :(得分:2)
取消引用end()
迭代器是非法的,这是在这个循环的第一次迭代中发生的事情:
for(std::list<std::shared_ptr<Shape>>::iterator it = m_view.Undo.end();
来自list::end()
参考页:
返回容器最后一个元素后面元素的迭代器。 该元素充当占位符; 尝试访问它会导致未定义的行为。
如果您希望向后迭代,请使用reverse_iterators
,rbegin()
和rend()
:
for (std::list<std::shared_ptr<Shape>>::reverse_iterator i(l.rbegin());
i != l.rend();
i++)
{
}
由于您有可用的c ++ 11功能(std::shared_ptr
),因此您可以使用auto
来推断iterator
类型,而不是显式输入:
for (auto i(l.rbegin()); i != l.rend(); i++)
{
}