<commit_before>#include "cozmo/cozmo.hpp"
#include "Eigen/Dense"
#include <cmath>

namespace cozmo{
using BoxShape = dart::dynamics::BoxShape;
using MeshShape = dart::dynamics::MeshShape;
using FreeJoint = dart::dynamics::FreeJoint;
using Joint = dart::dynamics::Joint;
using RevoluteJoint = dart::dynamics::RevoluteJoint;
using VisualAspect = dart::dynamics::VisualAspect;
using CollisionAspect = dart::dynamics::CollisionAspect;
using DynamicsAspect = dart::dynamics::DynamicsAspect;
using Skeleton = dart::dynamics::Skeleton;
using FixedFrame = dart::dynamics::FixedFrame;
  //using WorldPtr = dart::simulation::WorldPtr;
using World = dart::simulation::World;
using WeldJointConstraint = dart::constraint::WeldJointConstraint;

BodyNodePtr makeRootBody(const SkeletonPtr& cozmo, const std::string& name)
{
  FreeJoint::Properties properties;

  BodyNodePtr bn = cozmo->createJointAndBodyNodePair<FreeJoint>(
			  nullptr, properties,
			  dart::dynamics::BodyNode::AspectProperties(name)).second;

  // Make a shape for the Base
  std::shared_ptr<MeshShape> base(new MeshShape(
      Eigen::Vector3d(0., 0., 0.),
      MeshShape::loadMesh("/home/vinitha910/workspaces/cozmo_workspace/src/cozmo_description/meshes/cozmo_base.STL")));
  auto shapeNode = bn->createShapeNodeWith<VisualAspect>(std::static_pointer_cast<dart::dynamics::Shape>(base));

  Eigen::Isometry3d tf = Eigen::Isometry3d::Identity();
  Eigen::Matrix3d R = Eigen::Matrix3d::Identity();
  R = Eigen::AngleAxisd(-M_PI/2, Eigen::Vector3d::UnitX());
  tf.linear() = R;

  bn->getParentJoint()->setTransformFromChildBodyNode(tf);
  shapeNode->getVisualAspect()->setRGB(Eigen::Vector3d(202/255., 180/255., 148/255.));

  return bn;
}

BodyNodePtr addBody(const SkeletonPtr& cozmo, BodyNodePtr parent, const std::string& name, const std::string& filepath)
{
  RevoluteJoint::Properties properties;

  auto joint_bn = cozmo->createJointAndBodyNodePair<RevoluteJoint>(
			  parent, properties,
			  dart::dynamics::BodyNode::AspectProperties(name));
  auto bn = joint_bn.second;
  auto joint = joint_bn.first;

  std::shared_ptr<MeshShape> child(new MeshShape(Eigen::Vector3d(0., 0., 0.), MeshShape::loadMesh(filepath)));
  auto shapeNode = bn->createShapeNodeWith<VisualAspect>(std::static_pointer_cast<dart::dynamics::Shape>(child));

  Eigen::Isometry3d tf = Eigen::Isometry3d::Identity();
  Eigen::Matrix3d R = Eigen::Matrix3d::Identity();

  if (name == "head") {
    R = Eigen::AngleAxisd(M_PI/2, Eigen::Vector3d::UnitX());
    tf.linear() = R;
    shapeNode->setRelativeTransform(tf);
    shapeNode->setOffset(Eigen::Vector3d(0., 0.021, 0.032));
    shapeNode->getVisualAspect()->setRGB(Eigen::Vector3d(190/255., 190/255., 190/255.));
  } else if (name == "forklift") {
    shapeNode->getVisualAspect()->setRGB(Eigen::Vector3d(193/255., 24/255., 22/255.));

    Eigen::Vector3d T = Eigen::Vector3d(0.066, 0.001, 0.0032);
    tf.translation() = T;
    joint->setTransformFromParentBodyNode(tf);

    T =  Eigen::Vector3d(0.0028, 0.025, 0.0);
    tf.translation() = T;
    joint->setTransformFromChildBodyNode(tf);

    bn->getParentJoint()->setPosition(0, -0.12);
  } else if (name == "lower_forklift_strut_left_1" ||
	     name == "lower_forklift_strut_left_2") {
    shapeNode->getVisualAspect()->setRGB(Eigen::Vector3d(230/255., 230/255., 230/255.));

    Eigen::Vector3d T = Eigen::Vector3d(-0.004, 0.044, 0.0805);
    tf.translation() = T;
    joint->setTransformFromParentBodyNode(tf); //transfrom from parent moves joint and body node

    T = Eigen::Vector3d(0.006, 0.015, 0.0);
    tf.translation() = T;
    joint->setTransformFromChildBodyNode(tf); //transform from child moves only body node

    bn->getParentJoint()->setPosition(0, 0.07);
  } else if (name == "lower_forklift_strut_right_1") {
    shapeNode->getVisualAspect()->setRGB(Eigen::Vector3d(230/255., 230/255., 230/255.));

    Eigen::Vector3d T = Eigen::Vector3d(-0.004, 0.044, 0.0315);
    tf.translation() = T;
    joint->setTransformFromParentBodyNode(tf); //transfrom from parent moves joint and body node

    T = Eigen::Vector3d(0.006, 0.015, 0.0);
    tf.translation() = T;
    joint->setTransformFromChildBodyNode(tf); //transform from child moves only body node

    bn->getParentJoint()->setPosition(0, 0.07);
  } else if (name == "lower_forklift_strut_right_2") {
    shapeNode->getVisualAspect()->setRGB(Eigen::Vector3d(230/255., 230/255., 230/255.));

    Eigen::Vector3d T = Eigen::Vector3d(0.001, 0.014, 0.0);
    tf.translation() = T;
    joint->setTransformFromParentBodyNode(tf); //transfrom from parent moves joint and body node

    T = Eigen::Vector3d(0.0691, 0.0032, 0.0032);
    tf.translation() = T;
    joint->setTransformFromChildBodyNode(tf); //transform from child moves only body node

    bn->getParentJoint()->setPosition(0, 0.04);
  } else if (name == "upper_forklift_strut_left_1" ||
	     name == "upper_forklift_strut_left_2") {
    shapeNode->getVisualAspect()->setRGB(Eigen::Vector3d(230/255., 230/255., 230/255.));

    Eigen::Vector3d T = Eigen::Vector3d(-0.004, 0.058, 0.0805);
    tf.translation() = T;
    joint->setTransformFromParentBodyNode(tf); //transfrom from parent moves joint and body node

    T = Eigen::Vector3d(0.003, 0.021, 0.0);
    tf.translation() = T;
    joint->setTransformFromChildBodyNode(tf); //transform from child moves only body node

    bn->getParentJoint()->setPosition(0, 0.15);

  } else if (name == "upper_forklift_strut_right_1" ||
	     name == "upper_forklift_strut_right_2") {
    shapeNode->getVisualAspect()->setRGB(Eigen::Vector3d(230/255., 230/255., 230/255.));

    Eigen::Vector3d T = Eigen::Vector3d(-0.004, 0.058, 0.0315);
    tf.translation() = T;
    joint->setTransformFromParentBodyNode(tf); //transfrom from parent moves joint and body node

    T = Eigen::Vector3d(0.003, 0.021, 0.0);
    tf.translation() = T;
    joint->setTransformFromChildBodyNode(tf); //transform from child moves only body node

    bn->getParentJoint()->setPosition(0, 0.15);
  }

  return bn;
}

WorldPtr createCozmo()
{
  // Create a world and add the pendulum to the world
  WorldPtr world(new World);

  SkeletonPtr cozmo = Skeleton::create("cozmo");
  BodyNodePtr base = makeRootBody(cozmo, "body");
  // BodyNodePtr head = addBody(cozmo, base, "head",
  // 			   "/home/vinitha910/workspaces/cozmo_workspace/src/cozmo_description/meshes/head.STL");

  BodyNodePtr upper_forklift_strut_left_1 =
    addBody(cozmo, base, "upper_forklift_strut_left_1",
  	    "/home/vinitha910/workspaces/cozmo_workspace/src/cozmo_description/meshes/upper_forklift_strut.STL");
  BodyNodePtr upper_forklift_strut_right_1 =
    addBody(cozmo, base, "upper_forklift_strut_right_1",
            "/home/vinitha910/workspaces/cozmo_workspace/src/cozmo_description/meshes/upper_forklift_strut.STL");
  BodyNodePtr lower_forklift_strut_left_1 =
    addBody(cozmo, base, "lower_forklift_strut_left_1",
            "/home/vinitha910/workspaces/cozmo_workspace/src/cozmo_description/meshes/lower_forklift_strut.STL");
  BodyNodePtr lower_forklift_strut_right_1 =
    addBody(cozmo, base, "lower_forklift_strut_right_1",
            "/home/vinitha910/workspaces/cozmo_workspace/src/cozmo_description/meshes/lower_forklift_strut.STL");

  BodyNodePtr forklift = addBody(cozmo, upper_forklift_strut_right_1, "forklift",
  	                         "/home/vinitha910/workspaces/cozmo_workspace/src/cozmo_description/meshes/forklift.STL");

  BodyNodePtr lower_forklift_strut_right_2 =
    addBody(cozmo, forklift, "lower_forklift_strut_right_2",
            "/home/vinitha910/workspaces/cozmo_workspace/src/cozmo_description/meshes/lower_forklift_strut.STL");

  world->addSkeleton(cozmo);
  auto constraint = std::make_shared<WeldJointConstraint>(lower_forklift_strut_right_1, lower_forklift_strut_right_2);

  // world->getConstraintSolver()->addConstraint(constraint_1);
  // world->getConstraintSolver()->addConstraint(constraint_2);
  // world->getConstraintSolver()->addConstraint(constraint_3);
  // world->getConstraintSolver()->addConstraint(constraint_4);

  return world;
}
}

<commit_msg>head to base joint complete<commit_after>#include "cozmo/cozmo.hpp"
#include "Eigen/Dense"
#include <cmath>

namespace cozmo{
using BoxShape = dart::dynamics::BoxShape;
using MeshShape = dart::dynamics::MeshShape;
using FreeJoint = dart::dynamics::FreeJoint;
using Joint = dart::dynamics::Joint;
using RevoluteJoint = dart::dynamics::RevoluteJoint;
using VisualAspect = dart::dynamics::VisualAspect;
using CollisionAspect = dart::dynamics::CollisionAspect;
using DynamicsAspect = dart::dynamics::DynamicsAspect;
using Skeleton = dart::dynamics::Skeleton;
using FixedFrame = dart::dynamics::FixedFrame;
  //using WorldPtr = dart::simulation::WorldPtr;
using World = dart::simulation::World;
using WeldJointConstraint = dart::constraint::WeldJointConstraint;

BodyNodePtr makeRootBody(const SkeletonPtr& cozmo, const std::string& name)
{
  FreeJoint::Properties properties;

  BodyNodePtr bn = cozmo->createJointAndBodyNodePair<FreeJoint>(
			  nullptr, properties,
			  dart::dynamics::BodyNode::AspectProperties(name)).second;

  // Make a shape for the Base
  std::shared_ptr<MeshShape> base(new MeshShape(
      Eigen::Vector3d(0., 0., 0.),
      MeshShape::loadMesh("/home/vinitha910/workspaces/cozmo_workspace/src/cozmo_description/meshes/cozmo_base.STL")));
  auto shapeNode = bn->createShapeNodeWith<VisualAspect>(std::static_pointer_cast<dart::dynamics::Shape>(base));

  Eigen::Isometry3d tf = Eigen::Isometry3d::Identity();
  Eigen::Matrix3d R = Eigen::Matrix3d::Identity();
  R = Eigen::AngleAxisd(-M_PI/2, Eigen::Vector3d::UnitX());
  tf.linear() = R;

  bn->getParentJoint()->setTransformFromChildBodyNode(tf);
  shapeNode->getVisualAspect()->setRGB(Eigen::Vector3d(202/255., 180/255., 148/255.));

  return bn;
}

BodyNodePtr addBody(const SkeletonPtr& cozmo, BodyNodePtr parent, const std::string& name, const std::string& filepath)
{
  RevoluteJoint::Properties properties;

  auto joint_bn = cozmo->createJointAndBodyNodePair<RevoluteJoint>(
			  parent, properties,
			  dart::dynamics::BodyNode::AspectProperties(name));
  auto bn = joint_bn.second;
  auto joint = joint_bn.first;

  std::shared_ptr<MeshShape> child(new MeshShape(Eigen::Vector3d(0., 0., 0.), MeshShape::loadMesh(filepath)));
  auto shapeNode = bn->createShapeNodeWith<VisualAspect>(std::static_pointer_cast<dart::dynamics::Shape>(child));

  Eigen::Isometry3d tf = Eigen::Isometry3d::Identity();
  Eigen::Matrix3d R = Eigen::Matrix3d::Identity();

  if (name == "head") {
    shapeNode->getVisualAspect()->setRGB(Eigen::Vector3d(190/255., 190/255., 190/255.));

    Eigen::Vector3d T = Eigen::Vector3d(0.03, 0.0615, 0.0385);
    tf.translation() = T;
    joint->setTransformFromParentBodyNode(tf);

    T =  Eigen::Vector3d(0.022, 0.02, 0.0);
    tf.translation() = T;
    joint->setTransformFromChildBodyNode(tf);
  } else if (name == "forklift") {
    shapeNode->getVisualAspect()->setRGB(Eigen::Vector3d(193/255., 24/255., 22/255.));

    Eigen::Vector3d T = Eigen::Vector3d(0.066, 0.001, 0.0032);
    tf.translation() = T;
    joint->setTransformFromParentBodyNode(tf);

    T =  Eigen::Vector3d(0.0028, 0.025, 0.0);
    tf.translation() = T;
    joint->setTransformFromChildBodyNode(tf);

    bn->getParentJoint()->setPosition(0, -0.12);
  } else if (name == "lower_forklift_strut_left_1" ||
	     name == "lower_forklift_strut_left_2") {
    shapeNode->getVisualAspect()->setRGB(Eigen::Vector3d(230/255., 230/255., 230/255.));

    Eigen::Vector3d T = Eigen::Vector3d(-0.004, 0.044, 0.0805);
    tf.translation() = T;
    joint->setTransformFromParentBodyNode(tf); //transfrom from parent moves joint and body node

    T = Eigen::Vector3d(0.006, 0.015, 0.0);
    tf.translation() = T;
    joint->setTransformFromChildBodyNode(tf); //transform from child moves only body node

    bn->getParentJoint()->setPosition(0, 0.07);
  } else if (name == "lower_forklift_strut_right_1") {
    shapeNode->getVisualAspect()->setRGB(Eigen::Vector3d(230/255., 230/255., 230/255.));

    Eigen::Vector3d T = Eigen::Vector3d(-0.004, 0.044, 0.0315);
    tf.translation() = T;
    joint->setTransformFromParentBodyNode(tf); //transfrom from parent moves joint and body node

    T = Eigen::Vector3d(0.006, 0.015, 0.0);
    tf.translation() = T;
    joint->setTransformFromChildBodyNode(tf); //transform from child moves only body node

    bn->getParentJoint()->setPosition(0, 0.07);
  } else if (name == "lower_forklift_strut_right_2") {
    shapeNode->getVisualAspect()->setRGB(Eigen::Vector3d(230/255., 230/255., 230/255.));

    Eigen::Vector3d T = Eigen::Vector3d(0.001, 0.014, 0.0);
    tf.translation() = T;
    joint->setTransformFromParentBodyNode(tf); //transfrom from parent moves joint and body node

    T = Eigen::Vector3d(0.0691, 0.0032, 0.0032);
    tf.translation() = T;
    joint->setTransformFromChildBodyNode(tf); //transform from child moves only body node

    bn->getParentJoint()->setPosition(0, 0.04);
  } else if (name == "upper_forklift_strut_left_1" ||
	     name == "upper_forklift_strut_left_2") {
    shapeNode->getVisualAspect()->setRGB(Eigen::Vector3d(230/255., 230/255., 230/255.));

    Eigen::Vector3d T = Eigen::Vector3d(-0.004, 0.058, 0.0805);
    tf.translation() = T;
    joint->setTransformFromParentBodyNode(tf); //transfrom from parent moves joint and body node

    T = Eigen::Vector3d(0.003, 0.021, 0.0);
    tf.translation() = T;
    joint->setTransformFromChildBodyNode(tf); //transform from child moves only body node

    bn->getParentJoint()->setPosition(0, 0.15);

  } else if (name == "upper_forklift_strut_right_1" ||
	     name == "upper_forklift_strut_right_2") {
    shapeNode->getVisualAspect()->setRGB(Eigen::Vector3d(230/255., 230/255., 230/255.));

    Eigen::Vector3d T = Eigen::Vector3d(-0.004, 0.058, 0.0315);
    tf.translation() = T;
    joint->setTransformFromParentBodyNode(tf); //transfrom from parent moves joint and body node

    T = Eigen::Vector3d(0.003, 0.021, 0.0);
    tf.translation() = T;
    joint->setTransformFromChildBodyNode(tf); //transform from child moves only body node

    bn->getParentJoint()->setPosition(0, 0.15);
  }

  return bn;
}

WorldPtr createCozmo()
{
  // Create a world and add the pendulum to the world
  WorldPtr world(new World);

  SkeletonPtr cozmo = Skeleton::create("cozmo");
  BodyNodePtr base = makeRootBody(cozmo, "body");
  BodyNodePtr head = addBody(cozmo, base, "head",
  			   "/home/vinitha910/workspaces/cozmo_workspace/src/cozmo_description/meshes/head.STL");

  BodyNodePtr upper_forklift_strut_left_1 =
    addBody(cozmo, base, "upper_forklift_strut_left_1",
  	    "/home/vinitha910/workspaces/cozmo_workspace/src/cozmo_description/meshes/upper_forklift_strut.STL");
  BodyNodePtr upper_forklift_strut_right_1 =
    addBody(cozmo, base, "upper_forklift_strut_right_1",
            "/home/vinitha910/workspaces/cozmo_workspace/src/cozmo_description/meshes/upper_forklift_strut.STL");
  BodyNodePtr lower_forklift_strut_left_1 =
    addBody(cozmo, base, "lower_forklift_strut_left_1",
            "/home/vinitha910/workspaces/cozmo_workspace/src/cozmo_description/meshes/lower_forklift_strut.STL");
  BodyNodePtr lower_forklift_strut_right_1 =
    addBody(cozmo, base, "lower_forklift_strut_right_1",
            "/home/vinitha910/workspaces/cozmo_workspace/src/cozmo_description/meshes/lower_forklift_strut.STL");

  BodyNodePtr forklift = addBody(cozmo, upper_forklift_strut_right_1, "forklift",
  	                         "/home/vinitha910/workspaces/cozmo_workspace/src/cozmo_description/meshes/forklift.STL");

  BodyNodePtr lower_forklift_strut_right_2 =
    addBody(cozmo, forklift, "lower_forklift_strut_right_2",
            "/home/vinitha910/workspaces/cozmo_workspace/src/cozmo_description/meshes/lower_forklift_strut.STL");

  world->addSkeleton(cozmo);
  auto constraint = std::make_shared<WeldJointConstraint>(lower_forklift_strut_right_1, lower_forklift_strut_right_2);

  // world->getConstraintSolver()->addConstraint(constraint_1);
  // world->getConstraintSolver()->addConstraint(constraint_2);
  // world->getConstraintSolver()->addConstraint(constraint_3);
  // world->getConstraintSolver()->addConstraint(constraint_4);

  return world;
}
}

<|endoftext|>


<commit_before>// Time:  +:        O(d * t), t is the number of terms, d is the average degree of terms
//        -:        O(d * t)
//        *:        O(d * t^2)
//        eval:     O(d * t)
//        to_list:  O(d * tlogt)
// Space: O(e + d * t), e is the number of evalvars

class Poly {
public:
    Poly() {}

    Poly(const string& expr) {
        vector<string> key;
        if (is_number(expr)) {
            polies_[key] = stoi(expr);
        } else {
            key.emplace_back(expr);
            ++polies_[key];
        }
    }

    void update(const vector<string>& key, int val) {
        polies_[key] += val;
        if (polies_[key] == 0) {
            polies_.erase(key);
        }
    }

    operator vector<string>() {  // Time:  O(d * tlogt)
        map<vector<string>, int, Compare<vector<string>>> sorted(polies_.begin(), polies_.end());
        vector<string> result;
        for (const auto& kvp : sorted) {
            vector<string> tmp(kvp.first);
            tmp.emplace(tmp.begin(), to_string(kvp.second));
            result.emplace_back(join(tmp, "*"));
        }
        return result;
    }

    Poly operator+(const Poly &rhs) const {  // Time:  O(d * t)
        Poly result;
        for (const auto& kvp : polies_) {
            result.update(kvp.first, kvp.second);
        }
        for (const auto& kvp : rhs.polies_) {
            result.update(kvp.first, kvp.second);
        }
        return result;
    }

    Poly operator-(const Poly &rhs) const {  // Time:  O(d * t)
        Poly result;
        for (const auto& kvp : polies_) {
            result.update(kvp.first, kvp.second);
        }
        for (const auto& kvp : rhs.polies_) {
            result.update(kvp.first, -kvp.second);
        }
        return result;
    }

    Poly operator*(const Poly &rhs) const {  // Time:  O(d * t^2)
        Poly result;
        for (const auto& kvp1 : polies_) {
            for (const auto& kvp2 : rhs.polies_) {
                result.update(merge(kvp1.first, kvp2.first),
                              kvp1.second * kvp2.second);
            }
        }
        return result;
    }

    Poly eval(const unordered_map<string, int>& lookup) const {  // Time:  O(d * t)
        Poly result;
        for (const auto& kvp : polies_) {
            vector<string> key;
            int c = kvp.second;
            for (const auto& token : kvp.first) {
                if (lookup.count(token)) {
                    c *= lookup.at(token);
                } else {
                    key.emplace_back(token);
                }
            }
            result.update(key, c);
        }
        return result;
    }

private:
    bool is_number(const std::string &s) {
      return !s.empty() && std::all_of(s.begin(), s.end(), ::isdigit);
    }

    vector<string> merge(const vector<string>& arr1, const vector<string>& arr2) const {
        vector<string> result;
        int i = 0, j = 0;
        while (i < arr1.size() || j < arr2.size()) {
            if (j == arr2.size()) {
                result.emplace_back(arr1[i++]);
            } else if (i == arr1.size()) {
                result.emplace_back(arr2[j++]);
            } else if (arr1[i] < arr2[j]) {
                result.emplace_back(arr1[i++]);
            } else {
                result.emplace_back(arr2[j++]);
            }
        }
        return result;
    }

    string join(const vector<string>& strings, const string& delim) {
        if (strings.empty()) {
            return "";
        }
        ostringstream imploded;
        copy(strings.begin(), prev(strings.end()), ostream_iterator<string>(imploded, delim.c_str()));
        return imploded.str() + *prev(strings.end());
    }

    template<typename ContType>
    class Compare {
       public:
          bool operator()
              (const ContType& x,const ContType& y) {
              return x.size() != y.size() ? x.size() > y.size() : x < y;
          }
    };

    template<typename ContType>
    struct Hash {
        size_t operator()(const ContType& v) const {
            size_t seed = 0;
            for (const auto& i : v) {
                seed ^= std::hash<typename ContType::value_type>{}(i)  + 0x9e3779b9 + (seed<<6) + (seed>>2);
            }
            return seed;
        }
    };

    unordered_map<vector<string>, int, Hash<vector<string>>> polies_;
};

class Solution {
public:
    vector<string> basicCalculatorIV(string expression, vector<string>& evalvars, vector<int>& evalints) {
        unordered_map<string, int> lookup;
        for (int i = 0; i < evalvars.size(); ++i) {
            lookup[evalvars[i]] = evalints[i];
        }
        return parse(expression).eval(lookup);
    }

private:
    Poly parse(const string& s) {
        if (s.empty()) {
            return Poly();
        }
        stack<Poly> operands;
        stack<char> operators;
        string operand;
        for (int i = s.length() - 1; i >= 0; --i) {
            if (isalnum(s[i])) {
                operand.push_back(s[i]);
                if (i == 0 || !isalnum(s[i - 1])) {
                    reverse(operand.begin(), operand.end());
                    operands.emplace(Poly(operand));
                    operand.clear();
                }
            } else if (s[i] == ')' || s[i] == '*') {
                operators.emplace(s[i]);
            } else if (s[i] == '+' || s[i] == '-') {
                while (!operators.empty() && operators.top() == '*') {
                     compute(operands, operators);
                }
                operators.emplace(s[i]);
            } else if (s[i] == '(') {
                while (operators.top() != ')') {
                    compute(operands, operators);
                }
                operators.pop();
            }
        }
        while (!operators.empty()) {
            compute(operands, operators);
        }
        return operands.top();
    }

    template<typename T>
    void compute(stack<T>& operands, stack<char>& operators) {
        const auto left = operands.top();
        operands.pop();
        const auto right = operands.top();
        operands.pop();
        const char op = operators.top();
        operators.pop();
        if (op == '+') {
            operands.emplace(left + right);
        } else if (op == '-') {
            operands.emplace(left - right);
        } else if (op == '*') {
            operands.emplace(left * right);
        }
    }
};
<commit_msg>Update basic-calculator-iv.cpp<commit_after>// Time:  +:        O(d * t), t is the number of terms, d is the average degree of terms
//        -:        O(d * t)
//        *:        O(d * t^2)
//        eval:     O(d * t)
//        to_list:  O(d * tlogt)
// Space: O(e + d * t), e is the number of evalvars

class Poly {
public:
    Poly() {}

    Poly(const string& expr) {
        vector<string> key;
        if (is_number(expr)) {
            polies_[key] = stoi(expr);
        } else {
            key.emplace_back(expr);
            ++polies_[key];
        }
    }

    void update(const vector<string>& key, int val) {
        polies_[key] += val;
        if (polies_[key] == 0) {
            polies_.erase(key);
        }
    }

    operator vector<string>() {  // Time:  O(d * tlogt)
        map<vector<string>, int, Compare<vector<string>>> sorted(polies_.begin(), polies_.end());
        vector<string> result;
        for (const auto& kvp : sorted) {
            vector<string> tmp(kvp.first);
            tmp.emplace(tmp.begin(), to_string(kvp.second));
            result.emplace_back(join(tmp, "*"));
        }
        return result;
    }

    Poly operator+(const Poly &rhs) const {  // Time:  O(d * t)
        Poly result;
        for (const auto& kvp : polies_) {
            result.update(kvp.first, kvp.second);
        }
        for (const auto& kvp : rhs.polies_) {
            result.update(kvp.first, kvp.second);
        }
        return result;
    }

    Poly operator-(const Poly &rhs) const {  // Time:  O(d * t)
        Poly result;
        for (const auto& kvp : polies_) {
            result.update(kvp.first, kvp.second);
        }
        for (const auto& kvp : rhs.polies_) {
            result.update(kvp.first, -kvp.second);
        }
        return result;
    }

    Poly operator*(const Poly &rhs) const {  // Time:  O(d * t^2)
        Poly result;
        for (const auto& kvp1 : polies_) {
            for (const auto& kvp2 : rhs.polies_) {
                result.update(merge(kvp1.first, kvp2.first),
                              kvp1.second * kvp2.second);
            }
        }
        return result;
    }

    Poly eval(const unordered_map<string, int>& lookup) const {  // Time:  O(d * t)
        Poly result;
        for (const auto& kvp : polies_) {
            vector<string> key;
            int c = kvp.second;
            for (const auto& token : kvp.first) {
                if (lookup.count(token)) {
                    c *= lookup.at(token);
                } else {
                    key.emplace_back(token);
                }
            }
            result.update(key, c);
        }
        return result;
    }

private:
    bool is_number(const std::string &s) {
      return !s.empty() && std::all_of(s.begin(), s.end(), ::isdigit);
    }

    vector<string> merge(const vector<string>& arr1, const vector<string>& arr2) const {  // Time:  O(d)
        vector<string> result;
        int i = 0, j = 0;
        while (i < arr1.size() || j < arr2.size()) {
            if (j == arr2.size()) {
                result.emplace_back(arr1[i++]);
            } else if (i == arr1.size()) {
                result.emplace_back(arr2[j++]);
            } else if (arr1[i] < arr2[j]) {
                result.emplace_back(arr1[i++]);
            } else {
                result.emplace_back(arr2[j++]);
            }
        }
        return result;
    }

    string join(const vector<string>& strings, const string& delim) {
        if (strings.empty()) {
            return "";
        }
        ostringstream imploded;
        copy(strings.begin(), prev(strings.end()), ostream_iterator<string>(imploded, delim.c_str()));
        return imploded.str() + *prev(strings.end());
    }

    template<typename ContType>
    class Compare {
       public:
          bool operator()
              (const ContType& x,const ContType& y) {
              return x.size() != y.size() ? x.size() > y.size() : x < y;
          }
    };

    template<typename ContType>
    struct Hash {
        size_t operator()(const ContType& v) const {
            size_t seed = 0;
            for (const auto& i : v) {
                seed ^= std::hash<typename ContType::value_type>{}(i)  + 0x9e3779b9 + (seed<<6) + (seed>>2);
            }
            return seed;
        }
    };

    unordered_map<vector<string>, int, Hash<vector<string>>> polies_;
};

class Solution {
public:
    vector<string> basicCalculatorIV(string expression, vector<string>& evalvars, vector<int>& evalints) {
        unordered_map<string, int> lookup;
        for (int i = 0; i < evalvars.size(); ++i) {
            lookup[evalvars[i]] = evalints[i];
        }
        return parse(expression).eval(lookup);
    }

private:
    Poly parse(const string& s) {
        if (s.empty()) {
            return Poly();
        }
        stack<Poly> operands;
        stack<char> operators;
        string operand;
        for (int i = s.length() - 1; i >= 0; --i) {
            if (isalnum(s[i])) {
                operand.push_back(s[i]);
                if (i == 0 || !isalnum(s[i - 1])) {
                    reverse(operand.begin(), operand.end());
                    operands.emplace(Poly(operand));
                    operand.clear();
                }
            } else if (s[i] == ')' || s[i] == '*') {
                operators.emplace(s[i]);
            } else if (s[i] == '+' || s[i] == '-') {
                while (!operators.empty() && operators.top() == '*') {
                     compute(operands, operators);
                }
                operators.emplace(s[i]);
            } else if (s[i] == '(') {
                while (operators.top() != ')') {
                    compute(operands, operators);
                }
                operators.pop();
            }
        }
        while (!operators.empty()) {
            compute(operands, operators);
        }
        return operands.top();
    }

    template<typename T>
    void compute(stack<T>& operands, stack<char>& operators) {
        const auto left = operands.top();
        operands.pop();
        const auto right = operands.top();
        operands.pop();
        const char op = operators.top();
        operators.pop();
        if (op == '+') {
            operands.emplace(left + right);
        } else if (op == '-') {
            operands.emplace(left - right);
        } else if (op == '*') {
            operands.emplace(left * right);
        }
    }
};
<|endoftext|>


<commit_before>/*=========================================================================
 *
 *  Copyright NumFOCUS
 *
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at
 *
 *         http://www.apache.org/licenses/LICENSE-2.0.txt
 *
 *  Unless required by applicable law or agreed to in writing, software
 *  distributed under the License is distributed on an "AS IS" BASIS,
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the License for the specific language governing permissions and
 *  limitations under the License.
 *
 *=========================================================================*/

#include "itkXMLFileOutputWindow.h"
#include "itkTestingMacros.h"
#include <fstream>

int
itkXMLFileOutputWindowTest(int argc, char * argv[])
{
  if (argc < 1)
  {
    std::cerr << "Missing parameters." << std::endl;
    std::cerr << "Usage: " << itkNameOfTestExecutableMacro(argv) << " [filename]" << std::endl;
    return EXIT_FAILURE;
  }

  itk::XMLFileOutputWindow::Pointer logger = itk::XMLFileOutputWindow::New();

  ITK_EXERCISE_BASIC_OBJECT_METHODS(logger, XMLFileOutputWindow, FileOutputWindow);

  if (argc > 1)
  {
    logger->SetFileName(argv[1]);
  }

  logger->FlushOn();
  logger->AppendOn();

  logger->SetInstance(logger);

  // Check special cases
  const char * text = nullptr;
  logger->DisplayText(text);

  const char * specialCharText = "text&\"'<>";
  logger->DisplayText(specialCharText);

  // Regular cases
  const char * regularText = "text";
  logger->DisplayText(regularText);

  const char * errorText = "errorText";
  logger->DisplayErrorText(errorText);

  const char * warningText = "warningText";
  logger->DisplayWarningText(warningText);

  const char * genericOutputText = "genericOutputText";
  logger->DisplayGenericOutputText(genericOutputText);

  const char * debugText = "debugText";
  logger->DisplayDebugText(debugText);

  const char * tag = "tag";
  logger->DisplayTag(tag);

  // Check the number of lines written
  unsigned int  numLinesExpected = 7;
  unsigned int  numLinesRead = 0;
  std::ifstream in(logger->GetFileName());
  std::string   line;
  while (std::getline(in, line))
  {
    ++numLinesRead;
  }

  ITK_TEST_EXPECT_EQUAL(numLinesRead, numLinesExpected);

  std::cout << "Test finished." << std::endl;
  return EXIT_SUCCESS;
}
<commit_msg>BUG: Fix `itkXMLFileOutputWindowTest` regression<commit_after>/*=========================================================================
 *
 *  Copyright NumFOCUS
 *
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at
 *
 *         http://www.apache.org/licenses/LICENSE-2.0.txt
 *
 *  Unless required by applicable law or agreed to in writing, software
 *  distributed under the License is distributed on an "AS IS" BASIS,
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the License for the specific language governing permissions and
 *  limitations under the License.
 *
 *=========================================================================*/

#include "itkXMLFileOutputWindow.h"
#include "itkTestingMacros.h"
#include <fstream>
#include <cstdio>
#ifdef _WIN32
#  include <direct.h>
#  define cwd _getcwd
#  define OS_SEP "\\"
#else
#  include "unistd.h"
#  define cwd getcwd
#  define OS_SEP "/"
#endif

int
itkXMLFileOutputWindowTest(int argc, char * argv[])
{
  if (argc < 1)
  {
    std::cerr << "Missing parameters." << std::endl;
    std::cerr << "Usage: " << itkNameOfTestExecutableMacro(argv) << " [filename]" << std::endl;
    return EXIT_FAILURE;
  }

  itk::XMLFileOutputWindow::Pointer logger = itk::XMLFileOutputWindow::New();

  ITK_EXERCISE_BASIC_OBJECT_METHODS(logger, XMLFileOutputWindow, FileOutputWindow);

  if (argc > 1)
  {
    logger->SetFileName(argv[1]);
  }

  logger->FlushOn();
  logger->AppendOn();

  logger->SetInstance(logger);

  // If not input filename is provided, remove the contents in the existing file to avoid counting existing lines when
  // contents are appended
  if (argc == 1)
  {
    // In order to initialize the filename, some text needs to be written first
    const char * regularText = "text";
    logger->DisplayText(regularText);

    // Get the filename
    const char *      fileBaseName = logger->GetFileName();
    const std::size_t size = 4096;
    char              tmp[size];
    char *            status = cwd(tmp, size);
    if (!status)
    {
      std::cerr << "Test failed!" << std::endl;
      std::cerr << "Error getting the current directory. Cannot delete the contents of the target file: "
                << fileBaseName << std::endl;
      return EXIT_FAILURE;
    }
    std::string fileName = tmp + std::string(OS_SEP) + std::string(fileBaseName);

    // Delete the contents
    std::ofstream ofs;
    ofs.open(fileName, std::ofstream::out | std::ofstream::trunc);
    ofs.close();
  }

  // Check special cases
  const char * text = nullptr;
  logger->DisplayText(text);

  const char * specialCharText = "text&\"'<>";
  logger->DisplayText(specialCharText);

  // Regular cases
  const char * regularText = "text";
  logger->DisplayText(regularText);

  const char * errorText = "errorText";
  logger->DisplayErrorText(errorText);

  const char * warningText = "warningText";
  logger->DisplayWarningText(warningText);

  const char * genericOutputText = "genericOutputText";
  logger->DisplayGenericOutputText(genericOutputText);

  const char * debugText = "debugText";
  logger->DisplayDebugText(debugText);

  const char * tag = "tag";
  logger->DisplayTag(tag);

  // Check the number of lines written
  unsigned int  numLinesExpected = 7;
  unsigned int  numLinesRead = 0;
  std::ifstream in(logger->GetFileName());
  std::string   line;
  while (std::getline(in, line))
  {
    ++numLinesRead;
  }

  ITK_TEST_EXPECT_EQUAL(numLinesRead, numLinesExpected);

  std::cout << "Test finished." << std::endl;
  return EXIT_SUCCESS;
}
<|endoftext|>


<commit_before>/*===================================================================

The Medical Imaging Interaction Toolkit (MITK)

Copyright (c) German Cancer Research Center,
Division of Medical and Biological Informatics.
All rights reserved.

This software is distributed WITHOUT ANY WARRANTY; without
even the implied warranty of MERCHANTABILITY or FITNESS FOR
A PARTICULAR PURPOSE.

See LICENSE.txt or http://www.mitk.org for details.

===================================================================*/

#include "MiniAppManager.h"

// std includes
#include <string>
#include <sstream>

// ITK includes
#include <itkImageFileWriter.h>

// CTK includes
#include "ctkCommandLineParser.h"

// MITK includes
#include <mitkBaseDataIOFactory.h>
#include <mitkConnectomicsObjectFactory.h>
#include <mitkConnectomicsStatisticsCalculator.h>
#include <itkConnectomicsNetworkToConnectivityMatrixImageFilter.h>

int NetworkStatistics(int argc, char* argv[])
{
  ctkCommandLineParser parser;
  parser.setArgumentPrefix("--", "-");
  parser.addArgument("inputNetwork", "i", ctkCommandLineParser::String, "input connectomics network (.cnf)", us::Any(), false);
  parser.addArgument("outputFile", "o", ctkCommandLineParser::String, "name of output file", us::Any(), false);

  parser.addArgument("noGlobalStatistics", "g", ctkCommandLineParser::Bool, "Do not calculate global statistics");
  parser.addArgument("createConnectivityMatriximage", "I", ctkCommandLineParser::Bool, "Write connectivity matrix image");
  parser.addArgument("binaryConnectivity", "b", ctkCommandLineParser::Bool, "Whether to create a binary connectivity matrix");
  parser.addArgument("rescaleConnectivity", "r", ctkCommandLineParser::Bool, "Whether to rescale the connectivity matrix");

  map<string, us::Any> parsedArgs = parser.parseArguments(argc, argv);
  if (parsedArgs.size()==0)
    return EXIT_FAILURE;

  //default values
  bool noGlobalStatistics( false );
  bool binaryConnectivity( false );
  bool rescaleConnectivity( false );
  bool createConnectivityMatriximage( false );

  // parse command line arguments
  std::string networkName = us::any_cast<std::string>(parsedArgs["inputNetwork"]);
  std::string outName = us::any_cast<std::string>(parsedArgs["outputFile"]);

  if (parsedArgs.count("noGlobalStatistics"))
    noGlobalStatistics = us::any_cast<bool>(parsedArgs["noGlobalStatistics"]);
  if (parsedArgs.count("binaryConnectivity"))
    binaryConnectivity = us::any_cast<bool>(parsedArgs["binaryConnectivity"]);
  if (parsedArgs.count("rescaleConnectivity"))
    rescaleConnectivity = us::any_cast<bool>(parsedArgs["rescaleConnectivity"]);
  if (parsedArgs.count("createConnectivityMatriximage"))
    createConnectivityMatriximage = us::any_cast<bool>(parsedArgs["createConnectivityMatriximage"]);

  try
  {
    const std::string s1="", s2="";
    RegisterConnectomicsObjectFactory();

    // load network
    std::vector<mitk::BaseData::Pointer> networkFile =
      mitk::BaseDataIO::LoadBaseDataFromFile( networkName, s1, s2, false );
    if( networkFile.empty() )
    {
      std::string errorMessage = "File at " + networkName + " could not be read. Aborting.";
      MITK_ERROR << errorMessage;
      return EXIT_FAILURE;
    }
    mitk::BaseData* networkBaseData = networkFile.at(0);
    mitk::ConnectomicsNetwork* network = dynamic_cast<mitk::ConnectomicsNetwork*>( networkBaseData );

    if( !network )
    {
      std::string errorMessage = "Read file at " + networkName + " could not be recognized as network. Aborting.";
      MITK_ERROR << errorMessage;
      return EXIT_FAILURE;
    }

    mitk::ConnectomicsStatisticsCalculator::Pointer statisticsCalculator = mitk::ConnectomicsStatisticsCalculator::New();

    statisticsCalculator->SetNetwork( network );
    statisticsCalculator->Update();

    std::stringstream headerStream;

    // global statistics
    if( !noGlobalStatistics )
    {
      std::string globalOutName = outName + "_global.txt";
      headerStream  << "NumberOfVertices "
        << "NumberOfEdges "
        << "AverageDegree "
        << "ConnectionDensity "
        << "NumberOfConnectedComponents "
        << "AverageComponentSize "
        << "LargestComponentSize "
        << "RatioOfNodesInLargestComponent "
        << "HopPlotExponent "
        << "EffectiveHopDiameter "
        << "AverageClusteringCoefficientsC "
        << "AverageClusteringCoefficientsD "
        << "AverageClusteringCoefficientsE "
        << "AverageVertexBetweennessCentrality "
        << "AverageEdgeBetweennessCentrality "
        << "NumberOfIsolatedPoints "
        << "RatioOfIsolatedPoints "
        << "NumberOfEndPoints "
        << "RatioOfEndPoints "
        << "Diameter "
        << "Diameter90 "
        << "Radius "
        << "Radius90 "
        << "AverageEccentricity "
        << "AverageEccentricity90 "
        << "AveragePathLength "
        << "NumberOfCentralPoints "
        << "RatioOfCentralPoints "
        << "SpectralRadius "
        << "SecondLargestEigenValue "
        << "AdjacencyTrace "
        << "AdjacencyEnergy "
        << "LaplacianTrace "
        << "LaplacianEnergy "
        << "LaplacianSpectralGap "
        << "NormalizedLaplacianTrace "
        << "NormalizedLaplacianEnergy "
        << "NormalizedLaplacianNumberOf2s "
        << "NormalizedLaplacianNumberOf1s "
        << "NormalizedLaplacianNumberOf0s "
        << "NormalizedLaplacianLowerSlope "
        << "NormalizedLaplacianUpperSlope"
        << "SmallWorldness"
        << std::endl;

      std::stringstream dataStream;
      dataStream << statisticsCalculator->GetNumberOfVertices() << " "
        << statisticsCalculator->GetNumberOfEdges() << " "
        << statisticsCalculator->GetAverageDegree() << " "
        << statisticsCalculator->GetConnectionDensity() << " "
        << statisticsCalculator->GetNumberOfConnectedComponents() << " "
        << statisticsCalculator->GetAverageComponentSize() << " "
        << statisticsCalculator->GetLargestComponentSize() << " "
        << statisticsCalculator->GetRatioOfNodesInLargestComponent() << " "
        << statisticsCalculator->GetHopPlotExponent() << " "
        << statisticsCalculator->GetEffectiveHopDiameter() << " "
        << statisticsCalculator->GetAverageClusteringCoefficientsC() << " "
        << statisticsCalculator->GetAverageClusteringCoefficientsD() << " "
        << statisticsCalculator->GetAverageClusteringCoefficientsE() << " "
        << statisticsCalculator->GetAverageVertexBetweennessCentrality() << " "
        << statisticsCalculator->GetAverageEdgeBetweennessCentrality() << " "
        << statisticsCalculator->GetNumberOfIsolatedPoints() << " "
        << statisticsCalculator->GetRatioOfIsolatedPoints() << " "
        << statisticsCalculator->GetNumberOfEndPoints() << " "
        << statisticsCalculator->GetRatioOfEndPoints() << " "
        << statisticsCalculator->GetDiameter() << " "
        << statisticsCalculator->GetDiameter90() << " "
        << statisticsCalculator->GetRadius() << " "
        << statisticsCalculator->GetRadius90() << " "
        << statisticsCalculator->GetAverageEccentricity() << " "
        << statisticsCalculator->GetAverageEccentricity90() << " "
        << statisticsCalculator->GetAveragePathLength() << " "
        << statisticsCalculator->GetNumberOfCentralPoints() << " "
        << statisticsCalculator->GetRatioOfCentralPoints() << " "
        << statisticsCalculator->GetSpectralRadius() << " "
        << statisticsCalculator->GetSecondLargestEigenValue() << " "
        << statisticsCalculator->GetAdjacencyTrace() << " "
        << statisticsCalculator->GetAdjacencyEnergy() << " "
        << statisticsCalculator->GetLaplacianTrace() << " "
        << statisticsCalculator->GetLaplacianEnergy() << " "
        << statisticsCalculator->GetLaplacianSpectralGap() << " "
        << statisticsCalculator->GetNormalizedLaplacianTrace() << " "
        << statisticsCalculator->GetNormalizedLaplacianEnergy() << " "
        << statisticsCalculator->GetNormalizedLaplacianNumberOf2s() << " "
        << statisticsCalculator->GetNormalizedLaplacianNumberOf1s() << " "
        << statisticsCalculator->GetNormalizedLaplacianNumberOf0s() << " "
        << statisticsCalculator->GetNormalizedLaplacianLowerSlope() << " "
        << statisticsCalculator->GetNormalizedLaplacianUpperSlope() << " "
        << statisticsCalculator->GetSmallWorldness()
        << std::endl;

      ofstream outFile( globalOutName.c_str(), ios::out );

      if( ! outFile.is_open() )
      {
        std::string errorMessage = "Could not open " + globalOutName + " for writing.";
        MITK_ERROR << errorMessage;
        return EXIT_FAILURE;
      }

      outFile << headerStream.str() << dataStream.str();
      outFile.close();
    } // end global statistics

    //create connectivity matrix png
    if( createConnectivityMatriximage )
    {
      std::string connectivity_png_postfix = "_connectivity";
      if( binaryConnectivity )
      {
        connectivity_png_postfix += "_binary";
      }
      else if( rescaleConnectivity )
      {
        connectivity_png_postfix += "_rescaled";
      }
      connectivity_png_postfix += ".png";

      /* File format
      * A png file depicting the binary connectivity matrix
      */
      itk::ConnectomicsNetworkToConnectivityMatrixImageFilter::Pointer filter = itk::ConnectomicsNetworkToConnectivityMatrixImageFilter::New();
      filter->SetInputNetwork( network );
      filter->SetBinaryConnectivity( binaryConnectivity );
      filter->SetRescaleConnectivity( rescaleConnectivity );
      filter->Update();

      typedef itk::ConnectomicsNetworkToConnectivityMatrixImageFilter::OutputImageType connectivityMatrixImageType;

      itk::ImageFileWriter< connectivityMatrixImageType >::Pointer connectivityWriter = itk::ImageFileWriter< connectivityMatrixImageType >::New();

      connectivityWriter->SetInput( filter->GetOutput() );
      connectivityWriter->SetFileName( outName + connectivity_png_postfix);
      connectivityWriter->Update();

      MITK_INFO << "Connectivity matrix image written.";
    } // end create connectivity matrix png

    return EXIT_SUCCESS;
  }
  catch (itk::ExceptionObject e)
  {
    MITK_INFO << e;
    return EXIT_FAILURE;
  }
  catch (std::exception e)
  {
    MITK_INFO << e.what();
    return EXIT_FAILURE;
  }
  catch (...)
  {
    MITK_INFO << "ERROR!?!";
    return EXIT_FAILURE;
  }
  MITK_INFO << "DONE";
  return EXIT_SUCCESS;
}
RegisterDiffusionMiniApp(NetworkStatistics);
<commit_msg>Added local statistics capabilities<commit_after>/*===================================================================

The Medical Imaging Interaction Toolkit (MITK)

Copyright (c) German Cancer Research Center,
Division of Medical and Biological Informatics.
All rights reserved.

This software is distributed WITHOUT ANY WARRANTY; without
even the implied warranty of MERCHANTABILITY or FITNESS FOR
A PARTICULAR PURPOSE.

See LICENSE.txt or http://www.mitk.org for details.

===================================================================*/

#include "MiniAppManager.h"

// std includes
#include <string>
#include <sstream>
#include <vector>
#include <map>

// ITK includes
#include <itkImageFileWriter.h>

// CTK includes
#include "ctkCommandLineParser.h"

// MITK includes
#include <mitkBaseDataIOFactory.h>
#include <mitkConnectomicsObjectFactory.h>
#include <mitkConnectomicsStatisticsCalculator.h>
#include <itkConnectomicsNetworkToConnectivityMatrixImageFilter.h>

int NetworkStatistics(int argc, char* argv[])
{
  ctkCommandLineParser parser;
  parser.setArgumentPrefix("--", "-");
  parser.addArgument("inputNetwork", "i", ctkCommandLineParser::String, "input connectomics network (.cnf)", us::Any(), false);
  parser.addArgument("outputFile", "o", ctkCommandLineParser::String, "name of output file", us::Any(), false);

  parser.addArgument("noGlobalStatistics", "g", ctkCommandLineParser::Bool, "Do not calculate global statistics");
  parser.addArgument("createConnectivityMatriximage", "I", ctkCommandLineParser::Bool, "Write connectivity matrix image");
  parser.addArgument("binaryConnectivity", "b", ctkCommandLineParser::Bool, "Whether to create a binary connectivity matrix");
  parser.addArgument("rescaleConnectivity", "r", ctkCommandLineParser::Bool, "Whether to rescale the connectivity matrix");
  parser.addArgument("localStatistics", "L", ctkCommandLineParser::StringList, "Provide a list of node labels for local statistics", us::Any());

  map<string, us::Any> parsedArgs = parser.parseArguments(argc, argv);
  if (parsedArgs.size()==0)
    return EXIT_FAILURE;

  //default values
  bool noGlobalStatistics( false );
  bool binaryConnectivity( false );
  bool rescaleConnectivity( false );
  bool createConnectivityMatriximage( false );

  // parse command line arguments
  std::string networkName = us::any_cast<std::string>(parsedArgs["inputNetwork"]);
  std::string outName = us::any_cast<std::string>(parsedArgs["outputFile"]);

  ctkCommandLineParser::StringContainerType localLabels;

  if(parsedArgs.count("localStatistics"))
  {
    localLabels = us::any_cast<ctkCommandLineParser::StringContainerType>(parsedArgs["localStatistics"]);
  }

  if (parsedArgs.count("noGlobalStatistics"))
    noGlobalStatistics = us::any_cast<bool>(parsedArgs["noGlobalStatistics"]);
  if (parsedArgs.count("binaryConnectivity"))
    binaryConnectivity = us::any_cast<bool>(parsedArgs["binaryConnectivity"]);
  if (parsedArgs.count("rescaleConnectivity"))
    rescaleConnectivity = us::any_cast<bool>(parsedArgs["rescaleConnectivity"]);
  if (parsedArgs.count("createConnectivityMatriximage"))
    createConnectivityMatriximage = us::any_cast<bool>(parsedArgs["createConnectivityMatriximage"]);

  try
  {
    const std::string s1="", s2="";
    RegisterConnectomicsObjectFactory();

    // load network
    std::vector<mitk::BaseData::Pointer> networkFile =
      mitk::BaseDataIO::LoadBaseDataFromFile( networkName, s1, s2, false );
    if( networkFile.empty() )
    {
      std::string errorMessage = "File at " + networkName + " could not be read. Aborting.";
      MITK_ERROR << errorMessage;
      return EXIT_FAILURE;
    }
    mitk::BaseData* networkBaseData = networkFile.at(0);
    mitk::ConnectomicsNetwork* network = dynamic_cast<mitk::ConnectomicsNetwork*>( networkBaseData );

    if( !network )
    {
      std::string errorMessage = "Read file at " + networkName + " could not be recognized as network. Aborting.";
      MITK_ERROR << errorMessage;
      return EXIT_FAILURE;
    }

    mitk::ConnectomicsStatisticsCalculator::Pointer statisticsCalculator = mitk::ConnectomicsStatisticsCalculator::New();

    statisticsCalculator->SetNetwork( network );
    statisticsCalculator->Update();

    // global statistics
    if( !noGlobalStatistics )
    {
      std::string globalOutName = outName + "_global.txt";
      std::stringstream headerStream;
      headerStream  << "NumberOfVertices "
        << "NumberOfEdges "
        << "AverageDegree "
        << "ConnectionDensity "
        << "NumberOfConnectedComponents "
        << "AverageComponentSize "
        << "LargestComponentSize "
        << "RatioOfNodesInLargestComponent "
        << "HopPlotExponent "
        << "EffectiveHopDiameter "
        << "AverageClusteringCoefficientsC "
        << "AverageClusteringCoefficientsD "
        << "AverageClusteringCoefficientsE "
        << "AverageVertexBetweennessCentrality "
        << "AverageEdgeBetweennessCentrality "
        << "NumberOfIsolatedPoints "
        << "RatioOfIsolatedPoints "
        << "NumberOfEndPoints "
        << "RatioOfEndPoints "
        << "Diameter "
        << "Diameter90 "
        << "Radius "
        << "Radius90 "
        << "AverageEccentricity "
        << "AverageEccentricity90 "
        << "AveragePathLength "
        << "NumberOfCentralPoints "
        << "RatioOfCentralPoints "
        << "SpectralRadius "
        << "SecondLargestEigenValue "
        << "AdjacencyTrace "
        << "AdjacencyEnergy "
        << "LaplacianTrace "
        << "LaplacianEnergy "
        << "LaplacianSpectralGap "
        << "NormalizedLaplacianTrace "
        << "NormalizedLaplacianEnergy "
        << "NormalizedLaplacianNumberOf2s "
        << "NormalizedLaplacianNumberOf1s "
        << "NormalizedLaplacianNumberOf0s "
        << "NormalizedLaplacianLowerSlope "
        << "NormalizedLaplacianUpperSlope"
        << "SmallWorldness"
        << std::endl;

      std::stringstream dataStream;
      dataStream << statisticsCalculator->GetNumberOfVertices() << " "
        << statisticsCalculator->GetNumberOfEdges() << " "
        << statisticsCalculator->GetAverageDegree() << " "
        << statisticsCalculator->GetConnectionDensity() << " "
        << statisticsCalculator->GetNumberOfConnectedComponents() << " "
        << statisticsCalculator->GetAverageComponentSize() << " "
        << statisticsCalculator->GetLargestComponentSize() << " "
        << statisticsCalculator->GetRatioOfNodesInLargestComponent() << " "
        << statisticsCalculator->GetHopPlotExponent() << " "
        << statisticsCalculator->GetEffectiveHopDiameter() << " "
        << statisticsCalculator->GetAverageClusteringCoefficientsC() << " "
        << statisticsCalculator->GetAverageClusteringCoefficientsD() << " "
        << statisticsCalculator->GetAverageClusteringCoefficientsE() << " "
        << statisticsCalculator->GetAverageVertexBetweennessCentrality() << " "
        << statisticsCalculator->GetAverageEdgeBetweennessCentrality() << " "
        << statisticsCalculator->GetNumberOfIsolatedPoints() << " "
        << statisticsCalculator->GetRatioOfIsolatedPoints() << " "
        << statisticsCalculator->GetNumberOfEndPoints() << " "
        << statisticsCalculator->GetRatioOfEndPoints() << " "
        << statisticsCalculator->GetDiameter() << " "
        << statisticsCalculator->GetDiameter90() << " "
        << statisticsCalculator->GetRadius() << " "
        << statisticsCalculator->GetRadius90() << " "
        << statisticsCalculator->GetAverageEccentricity() << " "
        << statisticsCalculator->GetAverageEccentricity90() << " "
        << statisticsCalculator->GetAveragePathLength() << " "
        << statisticsCalculator->GetNumberOfCentralPoints() << " "
        << statisticsCalculator->GetRatioOfCentralPoints() << " "
        << statisticsCalculator->GetSpectralRadius() << " "
        << statisticsCalculator->GetSecondLargestEigenValue() << " "
        << statisticsCalculator->GetAdjacencyTrace() << " "
        << statisticsCalculator->GetAdjacencyEnergy() << " "
        << statisticsCalculator->GetLaplacianTrace() << " "
        << statisticsCalculator->GetLaplacianEnergy() << " "
        << statisticsCalculator->GetLaplacianSpectralGap() << " "
        << statisticsCalculator->GetNormalizedLaplacianTrace() << " "
        << statisticsCalculator->GetNormalizedLaplacianEnergy() << " "
        << statisticsCalculator->GetNormalizedLaplacianNumberOf2s() << " "
        << statisticsCalculator->GetNormalizedLaplacianNumberOf1s() << " "
        << statisticsCalculator->GetNormalizedLaplacianNumberOf0s() << " "
        << statisticsCalculator->GetNormalizedLaplacianLowerSlope() << " "
        << statisticsCalculator->GetNormalizedLaplacianUpperSlope() << " "
        << statisticsCalculator->GetSmallWorldness()
        << std::endl;

      ofstream outFile( globalOutName.c_str(), ios::out );

      if( ! outFile.is_open() )
      {
        std::string errorMessage = "Could not open " + globalOutName + " for writing.";
        MITK_ERROR << errorMessage;
        return EXIT_FAILURE;
      }

      outFile << headerStream.str() << dataStream.str();
      outFile.close();
    } // end global statistics

    //create connectivity matrix png
    if( createConnectivityMatriximage )
    {
      std::string connectivity_png_postfix = "_connectivity";
      if( binaryConnectivity )
      {
        connectivity_png_postfix += "_binary";
      }
      else if( rescaleConnectivity )
      {
        connectivity_png_postfix += "_rescaled";
      }
      connectivity_png_postfix += ".png";

      /* File format
      * A png file depicting the binary connectivity matrix
      */
      itk::ConnectomicsNetworkToConnectivityMatrixImageFilter::Pointer filter = itk::ConnectomicsNetworkToConnectivityMatrixImageFilter::New();
      filter->SetInputNetwork( network );
      filter->SetBinaryConnectivity( binaryConnectivity );
      filter->SetRescaleConnectivity( rescaleConnectivity );
      filter->Update();

      typedef itk::ConnectomicsNetworkToConnectivityMatrixImageFilter::OutputImageType connectivityMatrixImageType;

      itk::ImageFileWriter< connectivityMatrixImageType >::Pointer connectivityWriter = itk::ImageFileWriter< connectivityMatrixImageType >::New();

      connectivityWriter->SetInput( filter->GetOutput() );
      connectivityWriter->SetFileName( outName + connectivity_png_postfix);
      connectivityWriter->Update();

      MITK_INFO << "Connectivity matrix image written.";
    } // end create connectivity matrix png

    // calculate local averages
    if( localLabels.size() > 0 )
    {
      std::string localOutName = outName + "_local.txt";

      // Create LabelToIndex translation
      std::map< std::string, int > labelToIdMap;
      std::vector< mitk::ConnectomicsNetwork::NetworkNode > nodeVector = network->GetVectorOfAllNodes();
      for(int loop(0); loop < nodeVector.size(); loop++)
      {
        labelToIdMap.insert( std::pair< std::string, int>(nodeVector.at(loop).label, nodeVector.at(loop).id) );
      }

      std::vector< int > degreeVector = network->GetDegreeOfNodes();
      std::vector< double > ccVector = network->GetLocalClusteringCoefficients( );
      std::vector< double > bcVector = network->GetNodeBetweennessVector( );

      double sumDegree( 0 );
      double sumCC( 0 );
      double sumBC( 0 );
      double count( 0 );

      for( int loop(0); loop < localLabels.size(); loop++ )
      {
        if( network->CheckForLabel(localLabels.at( loop )) )
        {
          sumDegree = sumDegree + degreeVector.at( labelToIdMap.find( localLabels.at( loop ) )->second );
          sumCC = sumCC + ccVector.at( labelToIdMap.find( localLabels.at( loop ) )->second );
          sumBC = sumBC + bcVector.at( labelToIdMap.find( localLabels.at( loop ) )->second );
          count = count + 1;
        }
        else
        {
          MITK_ERROR << "Illegal label. Label: \"" << localLabels.at( loop ) << "\" not found.";
        }
      }

      std::stringstream headerStream;
      headerStream  << "LocalAverageDegree "
        << "LocalAverageCC "
        << "LocalAverageBC "
        << "NumberOfNodes"
        << std::endl;

      std::stringstream dataStream;
      dataStream  << sumDegree / count << " "
        << sumCC / count << " "
        << sumBC / count << " "
        << count
        << std::endl;

      ofstream outFile( localOutName.c_str(), ios::out );

      if( ! outFile.is_open() )
      {
        std::string errorMessage = "Could not open " + localOutName + " for writing.";
        MITK_ERROR << errorMessage;
        return EXIT_FAILURE;
      }

      outFile << headerStream.str() << dataStream.str();
      outFile.close();
    }// end calculate local averages

    return EXIT_SUCCESS;
  }
  catch (itk::ExceptionObject e)
  {
    MITK_INFO << e;
    return EXIT_FAILURE;
  }
  catch (std::exception e)
  {
    MITK_INFO << e.what();
    return EXIT_FAILURE;
  }
  catch (...)
  {
    MITK_INFO << "ERROR!?!";
    return EXIT_FAILURE;
  }
  MITK_INFO << "DONE";
  return EXIT_SUCCESS;
}
RegisterDiffusionMiniApp(NetworkStatistics);
<|endoftext|>


<commit_before>/******************************************************************************
 *                    _   _____   __________                                  *
 *                   | | / / _ | / __/_  __/     Visibility                   *
 *                   | |/ / __ |_\ \  / /          Across                     *
 *                   |___/_/ |_/___/ /_/       Space and Time                 *
 *                                                                            *
 * This file is part of VAST. It is subject to the license terms in the       *
 * LICENSE file found in the top-level directory of this distribution and at  *
 * http://vast.io/license. No part of VAST, including this file, may be       *
 * copied, modified, propagated, or distributed except according to the terms *
 * contained in the LICENSE file.                                             *
 ******************************************************************************/

#define SUITE evaluator

#include "vast/system/evaluator.hpp"

#include "vast/test/test.hpp"

#include "vast/test/fixtures/actor_system_and_events.hpp"

#include <vector>

#include "vast/concept/parseable/to.hpp"
#include "vast/concept/parseable/vast/expression.hpp"
#include "vast/expression.hpp"
#include "vast/system/atoms.hpp"

using namespace vast;

namespace {

using counts = std::vector<vast::count>;

template <class F>
ids select(const counts& xs, vast::count y, F pred) {
  ids result;
  for (auto x : xs)
    result.append_bits(pred(x, y), 1);
  return result;
}

ids select(const counts& xs, curried_predicate pred) {
  if (!caf::holds_alternative<vast::count>(pred.rhs))
    FAIL("RHS is not a count");
  auto y = caf::get<vast::count>(pred.rhs);
  switch (pred.op) {
    default:
      FAIL("unsupported relational operator");
    case equal:
      return select(xs, y, std::equal_to<>{});
    case not_equal:
      return select(xs, y, std::not_equal_to<>{});
    case less:
      return select(xs, y, std::less<>{});
    case less_equal:
      return select(xs, y, std::less_equal<>{});
    case greater:
      return select(xs, y, std::greater<>{});
    case greater_equal:
      return select(xs, y, std::greater_equal<>{});
  }
}

// Dummy actor representing an INDEXER for field `x`.
caf::behavior dummy_indexer(counts xs) {
  return {
    [xs = std::move(xs)](curried_predicate pred) { return select(xs, pred); }};
}

struct fixture : fixtures::deterministic_actor_system_and_events {
  fixture() {
    layout.fields.emplace_back("x", count_type{});
    layout.fields.emplace_back("y", count_type{});
    layout.name("test");
    // Spin up our dummies.
    auto& x_indexers= indexers["x"];
    add_indexer(x_indexers, {12, 42, 42, 13, 42, 75, 38, 11, 10});
    add_indexer(x_indexers, {42, 13, 17, 42, 99, 87, 23, 55, 11});
    auto& y_indexers= indexers["y"];
    add_indexer(y_indexers, {10, 10, 10, 10, 42, 10, 10, 10, 42});
    add_indexer(y_indexers, {10, 42, 10, 42, 42, 10, 10, 10, 10});
  }

  /// Maps predicates to a list of actors.
  std::map<std::string, std::vector<caf::actor>> indexers;

  void add_indexer(std::vector<caf::actor>& container, counts data) {
    container.emplace_back(sys.spawn(dummy_indexer, std::move(data)));
  }

  record_type layout;

  ids query(std::string_view expr_str) {
    auto expr = unbox(to<expression>(expr_str));
    evaluation_map qm;
    auto& triples = qm[layout];
    auto resolved = resolve(expr, layout);
    VAST_ASSERT(resolved.size() > 0);
    for (auto& [expr_position, pred]: resolved) {
      VAST_ASSERT(caf::holds_alternative<data_extractor>(pred.lhs));
      auto& dx = caf::get<data_extractor>(pred.lhs);
      std::string field_name = dx.offset.back() == 0 ? "x" : "y";
      auto& xs =  indexers[field_name];
      for (auto& x : xs)
        triples.emplace_back(expr_position, curried(pred), x);
    }
    auto eval = sys.spawn(system::evaluator, expr, std::move(qm));
    self->send(eval, self);
    run();
    ids result;
    while (!self->mailbox().empty())
      self->receive([&](const ids& hits) {
                    result |= hits; },
                    [](system::done_atom) {});
    return result;
  }
};

} // namespace

FIXTURE_SCOPE(evaluator_tests, fixture)

TEST(simple queries) {
  CHECK_EQUAL(query("x == 42"), make_ids({{0, 5}}, 9));
  CHECK_EQUAL(query("y != 10"), make_ids({1, 3, 4, 8}));
}

TEST(conjunctions) {
  CHECK_EQUAL(query("x == 42 && y != 10"), make_ids({1, 3, 4}, 9));
  CHECK_EQUAL(query("x == 42 && y != 10"), make_ids({1, 3, 4}, 9));
}

TEST(disjunctions) {
  CHECK_EQUAL(query("x == 42 || y != 10"), make_ids({{0, 5}, 8}, 9));
}

FIXTURE_SCOPE_END()
<commit_msg>Add more systematic tests for the EVALUATOR<commit_after>/******************************************************************************
 *                    _   _____   __________                                  *
 *                   | | / / _ | / __/_  __/     Visibility                   *
 *                   | |/ / __ |_\ \  / /          Across                     *
 *                   |___/_/ |_/___/ /_/       Space and Time                 *
 *                                                                            *
 * This file is part of VAST. It is subject to the license terms in the       *
 * LICENSE file found in the top-level directory of this distribution and at  *
 * http://vast.io/license. No part of VAST, including this file, may be       *
 * copied, modified, propagated, or distributed except according to the terms *
 * contained in the LICENSE file.                                             *
 ******************************************************************************/

#define SUITE evaluator

#include "vast/system/evaluator.hpp"

#include "vast/test/test.hpp"

#include "vast/test/fixtures/actor_system_and_events.hpp"

#include <vector>

#include "vast/concept/parseable/to.hpp"
#include "vast/concept/parseable/vast/expression.hpp"
#include "vast/expression.hpp"
#include "vast/system/atoms.hpp"

using namespace vast;

namespace {

using counts = std::vector<vast::count>;

template <class F>
ids select(const counts& xs, vast::count y, F pred) {
  ids result;
  for (auto x : xs)
    result.append_bits(pred(x, y), 1);
  return result;
}

ids select(const counts& xs, curried_predicate pred) {
  if (!caf::holds_alternative<vast::count>(pred.rhs))
    FAIL("RHS is not a count");
  auto y = caf::get<vast::count>(pred.rhs);
  switch (pred.op) {
    default:
      FAIL("unsupported relational operator");
    case equal:
      return select(xs, y, std::equal_to<>{});
    case not_equal:
      return select(xs, y, std::not_equal_to<>{});
    case less:
      return select(xs, y, std::less<>{});
    case less_equal:
      return select(xs, y, std::less_equal<>{});
    case greater:
      return select(xs, y, std::greater<>{});
    case greater_equal:
      return select(xs, y, std::greater_equal<>{});
  }
}

// Dummy actor representing an INDEXER for field `x`.
caf::behavior dummy_indexer(counts xs) {
  return {
    [xs = std::move(xs)](curried_predicate pred) { return select(xs, pred); }};
}

struct fixture : fixtures::deterministic_actor_system_and_events {
  fixture() {
    layout.fields.emplace_back("x", count_type{});
    layout.fields.emplace_back("y", count_type{});
    layout.name("test");
    // Spin up our dummies.
    auto& x_indexers= indexers["x"];
    add_indexer(x_indexers, {12, 42, 42, 17, 42, 75, 38, 11, 10});
    add_indexer(x_indexers, {42, 13, 17, 42, 99, 87, 23, 55, 11});
    auto& y_indexers= indexers["y"];
    add_indexer(y_indexers, {10, 10, 10, 10, 42, 10, 10, 10, 42});
    add_indexer(y_indexers, {10, 42, 10, 77, 42, 10, 10, 10, 10});
  }

  /// Maps predicates to a list of actors.
  std::map<std::string, std::vector<caf::actor>> indexers;

  void add_indexer(std::vector<caf::actor>& container, counts data) {
    container.emplace_back(sys.spawn(dummy_indexer, std::move(data)));
  }

  record_type layout;

  ids query(std::string_view expr_str) {
    auto expr = unbox(to<expression>(expr_str));
    evaluation_map qm;
    auto& triples = qm[layout];
    auto resolved = resolve(expr, layout);
    VAST_ASSERT(resolved.size() > 0);
    for (auto& [expr_position, pred]: resolved) {
      VAST_ASSERT(caf::holds_alternative<data_extractor>(pred.lhs));
      auto& dx = caf::get<data_extractor>(pred.lhs);
      std::string field_name = dx.offset.back() == 0 ? "x" : "y";
      auto& xs =  indexers[field_name];
      for (auto& x : xs)
        triples.emplace_back(expr_position, curried(pred), x);
    }
    auto eval = sys.spawn(system::evaluator, expr, std::move(qm));
    self->send(eval, self);
    run();
    ids result;
    bool got_done_atom = false;
    while (!self->mailbox().empty())
      self->receive([&](const ids& hits) { result |= hits; },
                    [&](system::done_atom) { got_done_atom = true; });
    if (!got_done_atom)
      FAIL("evaluator failed to send 'done'");
    return result;
  }
};

/// All of our indexers produce results of size 9.
constexpr size_t result_size = 9;

ids pad_result(ids x) {
  if (x.size() < result_size)
    x.append_bits(false, result_size - x.size());
  return x;
}

} // namespace

#define CHECK_QUERY(str, result)                                               \
  CHECK_EQUAL(pad_result(query(str)), pad_result(make_ids result));

FIXTURE_SCOPE(evaluator_tests, fixture)

TEST(simple queries) {
  MESSAGE("no hit in any indexer");
  CHECK_QUERY("x == 98", ({}));
  CHECK_QUERY("y <  10", ({}));
  MESSAGE("hits in one indexer");
  CHECK_QUERY("x == 13", ({1}));
  CHECK_QUERY("y >= 50", ({3}));
  MESSAGE("hits in more than one indexer");
  CHECK_QUERY("x == 42", ({{0, 5}}));
  CHECK_QUERY("y != 10", ({1, 3, 4, 8}));
}

TEST(conjunctions) {
  MESSAGE("no hit on either side");
  CHECK_QUERY("x == 33 && y >= 99", ({}));
  MESSAGE("hits on the left-hand side");
  CHECK_QUERY("x == 13 && y >= 99", ({}));
  MESSAGE("hits on the right-hand side");
  CHECK_QUERY("x == 33 && y != 10", ({}));
  MESSAGE("hits on both sides with intersection");
  CHECK_QUERY("x == 42 && y != 10", ({1, 3, 4}));
  MESSAGE("hits on both sides without intersection");
  CHECK_QUERY("x == 75 && y == 77", ({}));
}

TEST(disjunctions) {
  MESSAGE("no hit on either side");
  CHECK_QUERY("x == 33 || y >= 99", ({}));
  MESSAGE("hits on the left-hand side");
  CHECK_QUERY("x == 13 || y >= 99", ({1}));
  MESSAGE("hits on the right-hand side");
  CHECK_QUERY("x == 33 || y != 10", ({1, 3, 4, 8}));
  MESSAGE("hits on both sides with intersection");
  CHECK_QUERY("x == 42 || y != 10", ({0, 1, 2, 3, 4, 8}));
  MESSAGE("hits on both sides without intersection");
  CHECK_QUERY("x == 75 || y == 77", ({3, 5}));
}

FIXTURE_SCOPE_END()
<|endoftext|>


<commit_before>/*=========================================================================
 *
 *  Copyright Insight Software Consortium
 *
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at
 *
 *         http://www.apache.org/licenses/LICENSE-2.0.txt
 *
 *  Unless required by applicable law or agreed to in writing, software
 *  distributed under the License is distributed on an "AS IS" BASIS,
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the License for the specific language governing permissions and
 *  limitations under the License.
 *
 *=========================================================================*/
#include "itkMesh.h"
#include "itkMeshFileWriter.h"
#include "itkVTKPolyDataMeshIO.h"
#include "itkSymmetricSecondRankTensor.h"

int itkMeshFileWriteReadTensorTest( int argc, char* argv[] )
{
  if( argc < 3 )
    {
    std::cerr << "Usage: "
              << "<OutputMesh2D.vtk> "
              << "<OutputMesh3D.vtk> "
              << std::endl;
    return EXIT_FAILURE;
    }
  const char * outputMesh2D = argv[1];
  const char * outputMesh3D = argv[2];

  typedef float                                               TensorElementType;
  typedef itk::SymmetricSecondRankTensor<TensorElementType,2> Tensor2dType;
  typedef itk::SymmetricSecondRankTensor<TensorElementType,3> Tensor3dType;

  typedef itk::Mesh<Tensor2dType,2> Mesh2dType;
  typedef itk::Mesh<Tensor3dType,3> Mesh3dType;

  typedef itk::MeshFileWriter<Mesh2dType> MeshWriter2dType;
  typedef itk::MeshFileWriter<Mesh3dType> MeshWriter3dType;

  // Test the 2D case
  std::cout << "Testing VTKPolyDataMeshIO for a mesh with 2D tensor pixels..." << std::endl;

  Mesh2dType::PointType point2d;
  point2d.Fill( 1 );

  Mesh2dType::PixelType pixel2d;
  pixel2d.Fill( 0 );

  Mesh2dType::Pointer mesh2d = Mesh2dType::New();
  mesh2d->SetPoint( 0, point2d );
  mesh2d->SetPointData( 0, pixel2d );

  MeshWriter2dType::Pointer mesh2dWriter = MeshWriter2dType::New();
  mesh2dWriter->SetMeshIO( itk::VTKPolyDataMeshIO::New() );
  mesh2dWriter->SetInput( mesh2d );
  mesh2dWriter->SetFileName( outputMesh2D );
  try
    {
    mesh2dWriter->Update();
    }
  catch( itk::ExceptionObject &excp )
    {
    std::cerr << "Failed the VTKPolyDataMeshIO 2d test" << excp;
    return EXIT_FAILURE;
    }
  std::cout << "End of VTKPolyDataMeshIO 2D test. Completed successfully!" << std::endl << std::endl;

  // Test the 3D case
  std::cout << "Testing VTKPolyDataMeshIO for a mesh with 3D tensor pixels..." << std::endl;

  Mesh3dType::PointType point3d;
  point3d.Fill( 1 );

  Mesh3dType::PixelType pixel3d;
  pixel3d.Fill( 0 );

  Mesh3dType::Pointer mesh3d = Mesh3dType::New();
  mesh3d->SetPoint( 0, point3d );
  mesh3d->SetPointData( 0, pixel3d );

  MeshWriter3dType::Pointer mesh3dWriter = MeshWriter3dType::New();
  mesh3dWriter->SetMeshIO( itk::VTKPolyDataMeshIO::New() );
  mesh3dWriter->SetInput( mesh3d );
  mesh3dWriter->SetFileName( outputMesh3D );
  try
    {
    mesh3dWriter->Update();
    }
  catch( itk::ExceptionObject &excp )
    {
    std::cerr << "Failed the VTKPolyDataMeshIO 3D test" << excp;
    return EXIT_FAILURE;
    }
  std::cout << "End of VTKPolyDataMeshIO 3D test. Completed successfully!" << std::endl << std::endl;

  return EXIT_SUCCESS;
}
<commit_msg>ENH: Improve itkMeshFileWriter coverage<commit_after>/*=========================================================================
 *
 *  Copyright Insight Software Consortium
 *
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at
 *
 *         http://www.apache.org/licenses/LICENSE-2.0.txt
 *
 *  Unless required by applicable law or agreed to in writing, software
 *  distributed under the License is distributed on an "AS IS" BASIS,
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the License for the specific language governing permissions and
 *  limitations under the License.
 *
 *=========================================================================*/
#include "itkMesh.h"
#include "itkMeshFileWriter.h"
#include "itkVTKPolyDataMeshIO.h"
#include "itkSymmetricSecondRankTensor.h"
#include "itkTestingMacros.h"

int itkMeshFileWriteReadTensorTest( int argc, char* argv[] )
{
  if( argc < 3 )
    {
    std::cerr << "Usage: "
              << "<OutputMesh2D.vtk> "
              << "<OutputMesh3D.vtk> "
              << std::endl;
    return EXIT_FAILURE;
    }
  const char * outputMesh2D = argv[1];
  const char * outputMesh3D = argv[2];

  typedef float                                               TensorElementType;
  typedef itk::SymmetricSecondRankTensor<TensorElementType,2> Tensor2dType;
  typedef itk::SymmetricSecondRankTensor<TensorElementType,3> Tensor3dType;

  typedef itk::Mesh<Tensor2dType,2> Mesh2dType;
  typedef itk::Mesh<Tensor3dType,3> Mesh3dType;

  typedef itk::MeshFileWriter<Mesh2dType> MeshWriter2dType;
  typedef itk::MeshFileWriter<Mesh3dType> MeshWriter3dType;

  // Test the 2D case
  std::cout << "Testing VTKPolyDataMeshIO for a mesh with 2D tensor pixels..." << std::endl;

  Mesh2dType::PointType point2d;
  point2d.Fill( 1 );

  Mesh2dType::PixelType pixel2d;
  pixel2d.Fill( 0 );

  Mesh2dType::Pointer mesh2d = Mesh2dType::New();
  mesh2d->SetPoint( 0, point2d );
  mesh2d->SetPointData( 0, pixel2d );

  MeshWriter2dType::Pointer mesh2dWriter = MeshWriter2dType::New();

  EXERCISE_BASIC_OBJECT_METHODS( mesh2dWriter, MeshFileWriter, ProcessObject );

  mesh2dWriter->SetMeshIO( itk::VTKPolyDataMeshIO::New() );
  mesh2dWriter->SetInput( mesh2d );
  mesh2dWriter->SetFileName( outputMesh2D );
  try
    {
    mesh2dWriter->Update();
    }
  catch( itk::ExceptionObject &excp )
    {
    std::cerr << "Failed the VTKPolyDataMeshIO 2d test" << excp;
    return EXIT_FAILURE;
    }
  std::cout << "End of VTKPolyDataMeshIO 2D test. Completed successfully!" << std::endl << std::endl;

  // Test the 3D case
  std::cout << "Testing VTKPolyDataMeshIO for a mesh with 3D tensor pixels..." << std::endl;

  Mesh3dType::PointType point3d;
  point3d.Fill( 1 );

  Mesh3dType::PixelType pixel3d;
  pixel3d.Fill( 0 );

  Mesh3dType::Pointer mesh3d = Mesh3dType::New();
  mesh3d->SetPoint( 0, point3d );
  mesh3d->SetPointData( 0, pixel3d );

  MeshWriter3dType::Pointer mesh3dWriter = MeshWriter3dType::New();

  EXERCISE_BASIC_OBJECT_METHODS( mesh3dWriter, MeshFileWriter, ProcessObject );

  mesh3dWriter->SetMeshIO( itk::VTKPolyDataMeshIO::New() );
  mesh3dWriter->SetInput( mesh3d );
  mesh3dWriter->SetFileName( outputMesh3D );
  try
    {
    mesh3dWriter->Update();
    }
  catch( itk::ExceptionObject &excp )
    {
    std::cerr << "Failed the VTKPolyDataMeshIO 3D test" << excp;
    return EXIT_FAILURE;
    }
  std::cout << "End of VTKPolyDataMeshIO 3D test. Completed successfully!" << std::endl << std::endl;

  return EXIT_SUCCESS;
}
<|endoftext|>