C++ 责任链无缘无故地由指针返回

C++ 责任链无缘无故地由指针返回,c++,chain-of-responsibility,C++,Chain Of Responsibility,所以我有一个任务去做一个商店类,一个产品类,一个篮子类等等,我做了所有这些,经过测试,一切正常,这与问题无关。现在我要做的是创建折扣和责任链,比如说我创建了3个折扣,它通过指针和检查哪一个合适。所以我做了,它确实起作用了,当我调试的时候,我检查了一下,它停止在它需要的折扣上,返回给我折扣的价格,但是它不知何故通过指针返回,再次返回我不需要的东西。在展示代码之后,我将更清楚地说明这一点,并提供一个示例。这就是我的Discount.h,它有一个指向下一个折扣和主虚拟countDiscount()的指

所以我有一个任务去做一个商店类,一个产品类,一个篮子类等等,我做了所有这些,经过测试,一切正常,这与问题无关。现在我要做的是创建折扣和责任链,比如说我创建了3个折扣,它通过指针和检查哪一个合适。所以我做了,它确实起作用了,当我调试的时候,我检查了一下,它停止在它需要的折扣上,返回给我折扣的价格,但是它不知何故通过指针返回,再次返回我不需要的东西。在展示代码之后,我将更清楚地说明这一点,并提供一个示例。这就是我的
Discount.h
,它有一个指向下一个折扣和主虚拟
countDiscount()的指针在所有这一切中起作用的函数

#ifndef DISCOUNT_HEADER
#define DISCOUNT_HEADER

#include "Basket.h"

class Discount
{
public:
    Discount():next(NULL){}
    virtual int countDiscount(Basket b) = 0;
    void nextDiscount(Discount* nextDisc) { next = nextDisc; }
protected:
    Discount* next;
};

#endif
所以,我不得不做很多折扣类型,所以我从固定折扣开始,比如说我有
fixateddiscont(100,15)
,所以当一个人的篮子里的东西价值超过100时,就应用折扣,从他的总价值中减去15。因此,如果他购买的价格是110美元,那么这个折扣就是110-15=95。这是
FixatedDiscount.h

#ifndef FIXATED_HEADER
#define FIXATED_HEADER

#include "Discount.h"

class FixatedDiscount:public Discount
{
public:
    FixatedDiscount(int l, int d) : limit{ l }, discount{ d } {}
    int countDiscount(Basket b);
private:
    int limit;
    int discount;
};

#endif
这是
fixateddiscont.cpp

#include "FixatedDiscount.h"
#include <iostream>

int FixatedDiscount::countDiscount(Basket b) {
    int totalPrice = b.countPrice(); //this method just counts the value of the basket which for our example is 120
    if (totalPrice >= limit) {
        totalPrice -= discount;
        std::cout << "Handled when limit is " << limit << " and discount is: " << discount << " returning total price: " << totalPrice << std::endl;
    }
    else if (next != NULL) {
        next->countDiscount(b);
    }
    else {
        std::cout << "I am the last handler" << std::endl;
    }
    return totalPrice;
}
所以这里要做的是,正如您在
fixateddiscont.cpp
中看到的,我做了一个简单的
cout
来检查达到了哪个折扣,它说
在限额为100,折扣为:15时处理,返回的总价格为:105,这是应该的!但是,它不知何故再次通过
countDiscount
函数并返回
120
,这是没有折扣的价格,这怎么可能?它没有进入第三个折扣,但不知何故它再次通过该函数并返回120,因此我的理论是,当它达到第二个折扣时,它返回了我想要的东西,即
105
,因为应用了15的折扣,然后它返回到第一个指针,即第一个折扣,由于120不超过150,它不应用折扣并返回120。为什么它不把我想要的东西还给我,然后停下来?为什么它会再次通过该函数,可能会通过指针返回并再次应用已检查且不应再检查的折扣。

int fixateddiscont::countDiscount(篮子b){
int FixatedDiscount::countDiscount(Basket b) {
    int totalPrice = b.countPrice(); //this method just counts the value of the basket which for our example is 120
    if (totalPrice >= limit) {
        totalPrice -= discount;
        std::cout << "Handled when limit is " << limit << " and discount is: " << discount << " returning total price: " << totalPrice << std::endl;
    }
    else if (next != NULL) {
        next->countDiscount(b);
    }
    else {
        std::cout << "I am the last handler" << std::endl;
    }
    return totalPrice;
}
int totalPrice=b.countPrice();//此方法只计算篮子的值,对于我们的示例,篮子的值为120 如果(总价>=限额){ 总价-=折扣;
std::让你的
Discount
类同时充当折扣本身和手动链表的节点似乎是一种时髦的设计。你是否必须按照任务的要求这样做,或者你是否可以重构它,使每个折扣都是独立的,但是
countDiscount
需要一个Disco容器unts而不是单个折扣作为其参数?@NathanPierson我必须创建一个抽象类折扣,该类只具有计算折扣的方法,然后我必须创建折扣的子类,如FixatedDiscount、PercentDiscount和其他仅从折扣继承并使用其
countDiscount()
方法“包括参与问题的所有内容”-可以,但不包括
“Shop.h”
“Product.h”
“Basket.h”
您在再现问题时会产生问题。如果不需要这些问题,请将其从问题中删除。此外,通过将
NULL
替换为
nullptr
您将不需要包含您当前缺少的
,对于此特定示例,请注意
next->countDiscount(b)
将调用
countDiscount
,但它不会对返回值做任何处理。这意味着
fixated1->countDiscount(basket);
的返回值来自
return totalPrice;
,而您实际上希望它返回
next->countDiscount(b)
。当有其他人不需要关心的事情时,你的任务是在发布创造惊喜之前将其考虑在内。我不敢相信我会因为这么一个简单的错误而错过它,非常感谢!或者
return next->countDiscount(b);
因为调用
countDiscount()
都应该返回价格,如果该折扣有效的话
int FixatedDiscount::countDiscount(Basket b) {
    int totalPrice = b.countPrice(); //this method just counts the value of the basket which for our example is 120
    if (totalPrice >= limit) {
        totalPrice -= discount;
        std::cout << "Handled when limit is " << limit << " and discount is: " << discount << " returning total price: " << totalPrice << std::endl;
    }
    else if (next != NULL) {
        next->countDiscount(b);
    }
    else {
        std::cout << "I am the last handler" << std::endl;
    }
    return totalPrice;
}