从庸医(队列/堆栈)中包含的圆形数组顶部弹出一个项目



我目前正在尝试编写一个实现庸医(队列/堆栈)的程序。在每个庸医实例中,我都有一个指向字符数组"items"的指针我已经编写了pushBackpushFront函数,但我在编写popFrontpopBack函数时意识到,在这种情况下,我不知道如何从数组中取消引用元素。

我的老师给我提供了一个文本文件,说明程序的输出应该是什么样子,它需要看起来和他的完全一样。在他的输出文件中,当字符从数组的前面或后面弹出时,它会保留在内存中的那个位置,只是数组不再使用它。因此,当我将索引位置从数组的前面或后面弹出时,我不能将其设置回最初初始化的位置。这个字符需要保持在那里,所以当我运行代码时,即使它从数组中弹出,它仍然会显示出来,直到有东西被推到数组上覆盖它(数组的容量是静态的)。

注意:我的程序正在创建并写入一个单独的文本文件,该文件从数组的当前前面到后面显示数组元素,而不是从items[0]items[ccapacity-1],并且该文件在字符从数组中弹出后不会打印字符。

我有一个名为front的int变量,它包含数组的当前前索引位置,还有一个名为主back,它具有数组后面的索引位置。当我试图编写popFront函数时,我尝试做一些类似的事情

delete[] &items[front];

但这并没有奏效,也没有

delete[front] items;

让你知道我要做什么。我不知道我需要使用什么语法才能完成这项工作。我会在这里为您提供更多我的代码,这样您就可以亲眼看到:

Quack构造函数:(是的,我必须将数组中的元素初始化为"-",因为当他们还没有在输出文件中分配一个字母时,这就是他们需要的样子)。此外,还提供了growBy的实现,它可以放大数组,如果我想做这个赋值的更困难的版本并使数组动态,但我没有时间做那个,所以你可以忽略growBy

Quack::Quack(int capacity, int growBy) :
    capacity(capacity),
    growBy(growBy),
    nItems(0),
    items(new char[capacity]),
    front(NULL),
    back(NULL)
{
    for (int i = 0; i < capacity; i++)
    {
        items[i] = '-';
    }
}

这是我的Quack类:(我在类Quack中省略了printArray函数,因为它很长而且不相关)

class Quack
{
public:
    Quack(int capacity, int growBy = 0);
    // capacity: # of slots in array
    // growBy:   # of slots to add to array when it grows, 0 means "don't grow"
    ~Quack(void);
    bool pushFront(const char ch);      // push an item onto the front
    bool pushBack(const char ch);       // push an item onto the back
    bool popFront(char& ch);            // pop an item off the front
    bool popBack(char& ch);             // pop an item off the back
    void rotate(int r);                 // "rotate" the stored items (see note below)
    void reverse(void);                 // reverse the order of the stored items
    int itemCount(void);                // return the current number of stored items
private:
    char    *items;                     // pointer to storage for circular array,
                                            // each item in the array is a char
                                        // items is an array with 
    int     nItems;                     // # of items currently stored in array
    int     capacity;
    int     growBy;                     // # of slots in array
    int     front;
    int     back;
public:
    friend std::ostream& operator<<(std::ostream& out, Quack *q);
};

最后,这是我对popFront所做的操作(你可以看到元素取消引用需要去哪里;剩下的就是我在弹出项目后将front更改为正确的地方)。itemCount()是一个只返回nItems的函数,这是列表中的项目数,我也在跟踪它。

bool Quack::popFront(char& ch)
{
    // if list is empty, can't pop
    if (itemCount() == 0)
    {
        return false;
    }
    // pop front item
    /* here is where I don't know what to do, stackoverflow */
    // increment front and nItems
    if (front < (capacity - 2))
    {
        front++;
        nItems--;
        return false;
    }
    else if (front == (capacity - 1))
    {
        front = 0;
        nItems--;
        return false;
    }
    return false;
}

以下是VS中程序的正确输出,因此您可以看到它应该做什么:

(popFront从列表前面弹出项目,popBack从列表后面弹出项目,pushFront将项目添加到列表的前面,pushBack将项目添加至列表的后面)

pushFront(a)       [ a - - - - - - ]
pushFront(b)       [ a - - - - - b ]
pushFront(c)       [ a - - - - c b ]
pushFront(d)       [ a - - - d c b ]
pushBack(z)        [ a z - - d c b ]
pushFront(e)       [ a z - e d c b ]
popFront -> e      [ a z - e d c b ]
popFront -> d      [ a z - e d c b ]
pushBack(f)        [ a z f e d c b ]
pushBack(g)        [ a z f g d c b ]
rotate(2)          [ a z f g c b b ]
rotate(-3)         [ a z f g g c b ]
reverse            [ b c g g f z a ]
pushFront(y)       [ b c g y f z a ]
rotate(3)          [ b c g y f z a ]
rotate(-4)         [ b c g y f z a ]
popBack -> c       [ b c g y f z a ]
popBack -> b       [ b c g y f z a ]
popBack -> a       [ b c g y f z a ]
popBack -> z       [ b c g y f z a ]
popBack -> f       [ b c g y f z a ]
popBack -> y       [ b c g y f z a ]
popBack -> g       [ b c g y f z a ]

还有一点需要注意:我之所以不抛出任何异常,是因为我没有在其中包含任何队列实现。我仅有的库是fstream、iostream、ostream和iomanip(据我所知,根据任务的要求,我不能包括任何其他库)。

似乎没有像庸医或庸医异常这样的保留术语,所以在我抛出queueException的情况下,我只返回false(我想这就是为什么函数是bool类型的,我想不出任何其他原因:我们得到了函数原型,只是没有函数定义)。

非常感谢你抽出时间,哦,聪明的人!

您的变量items是一个数组。您可以delete整个阵列:

delete [] items;

或者不是delete,你不能分段删除一个元素。

ch由引用&传递,这意味着如果您为其赋值,则该值将被分配给传递到函数中的变量。如果没有&,作为参数传递的值将被复制到ch中,如果更改ch,则不会对原始参数产生任何影响。

指定给引用类似于指定给法线变量。引用指向与内存中另一个变量相同的数据,但它不是指针。引用只能"指向"另一个变量一次,但指针可以指向多次。

这里有一个例子:

// A silly example, which doubles the variable passed in
void doubleValue( int& i ) {
    i = i * 2;
}
// Sample use:
int j = 2;
doubleValue( j ); // j is now 4
doubleValue( j ); // j is now 8

因此,如果需要返回ch中弹出的值,可以使用数组访问,就像通常从数组中获取值一样。

char sample = items[front];

最新更新