summaryrefslogtreecommitdiff
path: root/graphs/cpp/caste_or_cast/nurturer.cc
blob: 09faa79636eea71b862f7ef5e404fc12617b5c59 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
#include "nurturer.hh"

#include <iostream>

// The Colony class was forward declared in Ant header
// We need to include its header here so we know Colony implementation
#include "colony.hh"
#include "provider.hh"

void Nurturer::feedLarvae()
{
    if (food_stock_ < 0.5)
        return;
    size_t count = 0;
    std::shared_ptr<Colony> colony = check_colony_access();
    for (auto i = colony->workers_.begin(); i < colony->workers_.end(); i++)
    {
        // if it doesn't have food anymore, can't feed more larvae
        if (food_stock_ < 0.5)
            break;
        std::shared_ptr<Worker> worker = *i;
        // only feed if it is a larvae and if it is not already full (its
        // food_level_ => 4)
        if (DevelopmentStage::LARVA == worker->get_stage()
            && worker->get_food_level() < 4)
        {
            worker->increment_food_level_by(0.5);
            food_stock_ -= 0.5;
            colony->cleanliness -= 0.3;
            food_level_ -= 0.03;
            count++;
        }
    }
    std::cout << count << " larvae were fed by nurturer.\n";
}

void Nurturer::work()
{
    if (stage_ != DevelopmentStage::ADULT)
        return;
    if (food_stock_ > 0.5)
    {
        // eat before working
        food_level_ += 0.5;
        food_stock_ -= 0.5;
        // complete its tasks
        feedLarvae();
        feedQueen();
        cleanNest();
    }
    else
        // make the ant more hungry
        food_level_ -= 0.042;
    //! call base class work() method
    Worker::work();
}
bool Nurturer::communicate(std::weak_ptr<Ant> wk_receiver)
{
    if (wk_receiver.lock() == nullptr)
        return false;
    if (!Ant::communicate(wk_receiver))
        return false;
    std::cout << "Nurturer initiates communication.\n";
    auto p = dynamic_cast<Provider*>(wk_receiver.lock().get());
    if (p)
    {
        p->transferFood(*this);
    }
    return true;
}
void Nurturer::feedQueen()
{
    if (food_stock_ < 1)
        return;
    std::cout << "Feeding Queen.\n";
    auto c = check_colony_access();
    c->queen_->increment_food_level_by(1);
    food_stock_--;
    if (static_cast<int>(c->queen_->get_food_level()) > 0
        && static_cast<int>(c->queen_->get_food_level()) % 6 == 0)
        c->queen_->layEgg();
    c->cleanliness -= .2;
}

void Nurturer::cleanNest()
{
    std::shared_ptr<Colony> colony = check_colony_access();
    if (colony->cleanliness < 100)
    {
        // clean the nest according to the luck of the Nurturer
        std::cout << "Cleaning nest: gained " << luck_ << " of cleanliness.\n";
        auto cleanliness = colony->cleanliness + luck_;
        colony->cleanliness = (cleanliness > 100) ? 100 : cleanliness;
    }
}

// FIXME : Implements communicate(std::weak_ptr<Ant>) virtual overridden method
// and feedQueen()