Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

add test code refs #126 #291

Draft
wants to merge 10 commits into
base: devel
Choose a base branch
from
Draft
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
update faultTreeUtils.C Ref #126
  • Loading branch information
Hugo Nie authored Mar 30, 2020
commit 8a6080dae6883b11063d82de48c4f76f693bebdf
60 changes: 54 additions & 6 deletions src/utils/FaultTreeUtils.C
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,10 @@ FTAUtils::FaultTree::FaultTree(std::string file_name, std::string root)
FTAUtils::Parser parser = FTAUtils::Parser(file_name, FTAUtils::Parser::FORMAT_CSV);
buildTree(parser);

// Override root node if not default
if (root != "")
{
// ASSERT
if (!(getNode(root)))
{
fprintf(stderr,
Expand All @@ -34,16 +36,21 @@ FTAUtils::FaultTree::FaultTree(set_string & sets_link, std::map<std::string, ft_
std::string root = "";
_node_d_b = _node_base;

// Clearing up sets vector for safety
rmSets();

// Add root to set
std::set<std::string> root_set, sub_sets;
root_set.insert("TOP");
root_set.insert("TOP"); // "TOP", size: 1

_sets.insert(root_set);

// Start with root node to expand on heirarchy
cutSetsExpand(getNode("TOP"));


// Check if first row is empty
// NOTE: Since its std::set, only first row could
// be empty
if (_sets.begin()->size() == 0)
{
_sets.erase(_sets.begin());
Expand All @@ -64,17 +71,22 @@ FTAUtils::FaultTree::buildTree(FTAUtils::Parser parser)
{
line = parser.yieldLine();

// Stop if no new line to process
if (line.size() == 0)
break;

// Stash name, operator
_node * node = new _node(line[0], str2Operator(line[1]));

// Add children
for (int i = 2; i < line.size(); i++)
node->_child.push_back(line[i]);

// Stash the first entry as ROOT of tree
if (_node_d_b.size() == 0)
_root = line[0];

// Add the newly created node to node lookup hashmap
_node_d_b[line[0]] = node;
}

Expand All @@ -85,6 +97,7 @@ FTAUtils::FaultTree::_operator_t
FTAUtils::FaultTree::str2Operator(std::string op)
{
std::string op_s = FTAUtils::str2Upper(op, true);
// ASSERT
if (_opDict.count(op_s) == 0)
{
fprintf(stderr,
Expand All @@ -101,16 +114,21 @@ FTAUtils::FaultTree::str2Operator(std::string op)
set_string
FTAUtils::FaultTree::computeMinimumCutSets()
{
// Clearing up sets vector for safety
rmSets();

// Add root to set
std::set<std::string> root_set, sub_sets;
root_set.insert(getRoot());

_sets.insert(root_set);

// Start with root node to expand on heirarchy
cutSetsExpand(getNode(getRoot()));


// Check if first row is empty
// NOTE: Since its std::set, only first row could
// be empty
if (_sets.begin()->size() == 0)
{
_sets.erase(_sets.begin());
Expand All @@ -136,8 +154,10 @@ FTAUtils::FaultTree::removeSubsets()
includes(row2_it->begin(), row2_it->end(), row1_it->begin(), row1_it->end());
bool row2_is_subset =
includes(row1_it->begin(), row1_it->end(), row2_it->begin(), row2_it->end());
// Remove row1 if row2 is a subset of row1 by marking it
if (row2_is_subset)
rm_its.insert(index1);
// Remove row2 if row1 is a subset of row1 by marking it
else if (row1_is_subset)
rm_its.insert(index2);
index2++;
Expand All @@ -146,6 +166,7 @@ FTAUtils::FaultTree::removeSubsets()
}

uint64_t index = 0;
// Remove rows marked to be removed
for (std::set<uint64_t>::iterator it = rm_its.begin(); it != rm_its.end(); ++it)
{
_sets.erase(next(_sets.begin(), *it - index));
Expand All @@ -156,6 +177,7 @@ FTAUtils::FaultTree::removeSubsets()
void
FTAUtils::FaultTree::cutSetsExpand(_node * node)
{
// ASSERT
if (!node)
{
fprintf(stderr,
Expand All @@ -166,6 +188,7 @@ FTAUtils::FaultTree::cutSetsExpand(_node * node)
abort();
}

// ASSERT
if (node->_child.size() == 0)
{
fprintf(stderr,
Expand All @@ -177,40 +200,50 @@ FTAUtils::FaultTree::cutSetsExpand(_node * node)
abort();
}


// New rows which have to be appended at end. Adding them might
// result in data hazards
set_string mk_rows;

// 1. Iterate through entire list and match for own node's name
for (set_string::iterator row_it = _sets.begin(); row_it != _sets.end(); ++row_it)
{
std::set<std::string> row(*row_it);
// Search for the element in row
std::set<std::string>::iterator it = find(row.begin(), row.end(), node->_name);
if (it != row.end())
{
// Erase self to add children
row.erase(it);


// 2. Replace self with children based on operation
// (i) . Replace self with children in same row if AND
// (ii). Replace self with child one per row if OR
switch (node->_op)
{
case AND:
// Append all children in same row
for (uint64_t c_id = 0; c_id < node->_child.size(); c_id++)
{
row.insert(node->_child[c_id]);
}
break;

case OR:
// Replicate line and append one child per row
for (uint64_t c_id = 0; c_id < node->_child.size(); c_id++)
{
std::set<std::string> row_set(row);
row_set.insert(node->_child[c_id]);
mk_rows.insert(row_set);
}

// Clear this row to be removed at end (postprocessing)
row.clear();
break;

default:
{
// ASSERT
fprintf(stderr,
"[ASSERT] In File: %s, Line: %d => "
"Unknown Operator found!.\n",
Expand All @@ -222,17 +255,22 @@ FTAUtils::FaultTree::cutSetsExpand(_node * node)
}
}


// The following 2 lines might result in an empty row to be pushed.
// If we gate insertion with count, we might have a data hazard due
// to wrong increment of iterators.
// A quick fix to this is to check for first row and delete it at end
_sets.erase(row_it);
_sets.insert(row);
}

// Add newly created rows
for (set_string::iterator it = mk_rows.begin(); it != mk_rows.end(); ++it)
{
std::set<std::string> row(*it);
_sets.insert(*it);
}

// 3. Recurse on each non leaf child
for (uint64_t c_id = 0; c_id < node->_child.size(); c_id++)
{
_node * child = getNode(node->_child[c_id]);
Expand Down Expand Up @@ -270,6 +308,7 @@ FTAUtils::FaultTree::getCutSets()

FTAUtils::Parser::Parser(std::string fileName, FTAUtils::Parser::parseFormatT format)
{
// Assertion on supported parsing formats
if (format != FORMAT_CSV)
{
fprintf(stderr,
Expand Down Expand Up @@ -298,6 +337,7 @@ FTAUtils::Parser::yieldLines()
{
line = FTAUtils::Parser::yieldLine();

// Stop if no new line to process
if (line.size() == 0)
break;
lines.push_back(line);
Expand All @@ -308,6 +348,7 @@ FTAUtils::Parser::yieldLines()
std::vector<std::string>
FTAUtils::Parser::yieldLine()
{
// ASSERT
if (!(fileP->is_open()))
{
fprintf(stderr,
Expand All @@ -321,6 +362,7 @@ FTAUtils::Parser::yieldLine()
std::string buffer;
std::vector<std::string> line;

// Get a line that has something except \n
if (getline(*fileP, buffer))
{
std::string token;
Expand Down Expand Up @@ -364,8 +406,10 @@ FTAUtils::interpolate(vector_double data, double x, bool extrapolate)
{
int size = data.size();

// find left end of interval for interpolation
int i = 0;

// special case: beyond right end
if (x >= data[size - 2][0])
{
i = size - 2;
Expand All @@ -376,8 +420,10 @@ FTAUtils::interpolate(vector_double data, double x, bool extrapolate)
i++;
}

// points on either side (unless beyond ends)
double xL = data[i][0], yL = data[i][1], xR = data[i + 1][0], yR = data[i + 1][1];

// if beyond ends of array and not extrapolating
if (!extrapolate)
{
if (x < xL)
Expand All @@ -386,8 +432,10 @@ FTAUtils::interpolate(vector_double data, double x, bool extrapolate)
yL = yR;
}

// gradient
double dydx = (yR - yL) / (xR - xL);

// linear interpolation
return yL + dydx * (x - xL);
}

Expand Down