Skip to content
Snippets Groups Projects
frictionpotential.hh 5.05 KiB
Newer Older
#ifndef DUNE_TECTONIC_FRICTIONPOTENTIAL_HH
#define DUNE_TECTONIC_FRICTIONPOTENTIAL_HH
Elias Pipping's avatar
Elias Pipping committed

Elias Pipping's avatar
Elias Pipping committed
#include <algorithm>
Elias Pipping's avatar
Elias Pipping committed
#include <cassert>
Elias Pipping's avatar
Elias Pipping committed
#include <cmath>
Elias Pipping's avatar
Elias Pipping committed
#include <limits>
Elias Pipping's avatar
Elias Pipping committed

Elias Pipping's avatar
Elias Pipping committed
#include <dune/common/exceptions.hh>
Elias Pipping's avatar
Elias Pipping committed
#include <dune/common/function.hh>

podlesny's avatar
podlesny committed
#include "frictiondata.hh"
class FrictionPotential {
  virtual ~FrictionPotential() {}
  double virtual differential(double s) const = 0;
  double virtual second_deriv(double x) const = 0;
  double virtual regularity(double s) const = 0;
  double virtual coefficientOfFriction(double s) const = 0;
  double virtual evaluate(double x) const {
    DUNE_THROW(Dune::NotImplemented, "evaluation not implemented");
  void virtual updateAlpha(double) = 0;
class TruncatedRateState : public FrictionPotential {
Elias Pipping's avatar
Elias Pipping committed
public:
  TruncatedRateState(double _weight, double _weightedNormalStress,
                     FrictionData _fd)
      : fd(_fd), weight(_weight), weightedNormalStress(_weightedNormalStress) {}
Elias Pipping's avatar
Elias Pipping committed

Elias Pipping's avatar
Elias Pipping committed
  double coefficientOfFriction(double V) const override {
    if (V <= Vmin)
Elias Pipping's avatar
Elias Pipping committed
      return 0.0;
Elias Pipping's avatar
Elias Pipping committed

    //std::cout << "V: " << V << " Vmin: " << Vmin << std::endl;

    auto res = fd.a * std::log(V / Vmin);
    if (std::isinf(res)) {
podlesny's avatar
podlesny committed
        //std::cout << "V: " << V << " Vmin: " << Vmin << std::endl;
Elias Pipping's avatar
Elias Pipping committed
  double differential(double V) const override {
podlesny's avatar
.  
podlesny committed
    //std::cout << "differential: " <<  weight * fd.C - weightedNormalStress * coefficientOfFriction(V) << std::endl;
    //if (V <= Vmin or regularity(V)>10e8)
    //  return 0.0;
podlesny's avatar
podlesny committed

    return weight * fd.C - weightedNormalStress * coefficientOfFriction(V);
podlesny's avatar
.  
podlesny committed
  double second_deriv(double V) const override {
    //std::cout << "second deriv: " << ((V<=Vmin) ? 0.0 : -weightedNormalStress * (fd.a / V)) << std::endl;

podlesny's avatar
podlesny committed
    if (V <= Vmin)
podlesny's avatar
.  
podlesny committed
      return 0.0;
podlesny's avatar
podlesny committed
    return - weightedNormalStress * (fd.a / V);
Elias Pipping's avatar
Elias Pipping committed
  double regularity(double V) const override {
podlesny's avatar
.  
podlesny committed
    //std::cout << "regularity: " << ((std::abs(V - Vmin) < 1e-14) ? std::numeric_limits<double>::infinity() : std::abs(second_deriv(V))) << std::endl;

    if (std::abs(V - Vmin) < 1e-14) // TODO
Elias Pipping's avatar
Elias Pipping committed
      return std::numeric_limits<double>::infinity();

Elias Pipping's avatar
Elias Pipping committed
    return std::abs(second_deriv(V));
podlesny's avatar
podlesny committed
  double evaluate(double V) const override {
    if (V <= Vmin)
podlesny's avatar
podlesny committed
        return 0.0;

      return weight * fd.C * V - weightedNormalStress * fd.a * V * (std::log(V / Vmin) - 1);
  }

Elias Pipping's avatar
Elias Pipping committed
  void updateAlpha(double alpha) override {
    double const logrest = (fd.mu0 + fd.b * alpha) / fd.a;
    Vmin = fd.V0 / std::exp(logrest);
podlesny's avatar
podlesny committed
    //Vmin = 0.0;
Elias Pipping's avatar
Elias Pipping committed
  }

Elias Pipping's avatar
Elias Pipping committed
private:
  FrictionData const fd;
  double const weight;
  double const weightedNormalStress;
  double Vmin;
class RegularisedRateState : public FrictionPotential {
public:
  RegularisedRateState(double _weight, double _weightedNormalStress,
                       FrictionData _fd)
      : fd(_fd), weight(_weight), weightedNormalStress(_weightedNormalStress) {}
Elias Pipping's avatar
Elias Pipping committed
  double coefficientOfFriction(double V) const override {
    return fd.a * std::asinh(0.5 * V / Vmin);
  }

Elias Pipping's avatar
Elias Pipping committed
  double differential(double V) const override {
    return weight * fd.C - weightedNormalStress * coefficientOfFriction(V);
Elias Pipping's avatar
Elias Pipping committed
  double second_deriv(double V) const override {
    return -weightedNormalStress * fd.a / std::hypot(2.0 * Vmin, V);
Elias Pipping's avatar
Elias Pipping committed
  double regularity(double V) const override {
    return std::abs(second_deriv(V));
  }
podlesny's avatar
podlesny committed
  double evaluate(double V) const override {
      return weight * fd.C * V - weightedNormalStress * 4 * fd.a * Vmin * std::pow(std::asinh(0.25 * V / Vmin), 2.0);
  }

Elias Pipping's avatar
Elias Pipping committed
  void updateAlpha(double alpha) override {
    double const logrest = (fd.mu0 + fd.b * alpha) / fd.a;
    Vmin = fd.V0 / std::exp(logrest);
  }

private:
  FrictionData const fd;
  double const weight;
  double const weightedNormalStress;
class Tresca : public FrictionPotential {
public:
  Tresca(double _weight, double _weightedNormalStress, FrictionData _fd)
      : fd(_fd), weightedNormalStress(_weightedNormalStress) {}

  double coefficientOfFriction(double V) const override {
    return fd.mu0;
  }

  double differential(double V) const override {
podlesny's avatar
podlesny committed
    //if (std::isinf(regularity(V)))
    //    return 0.0;
    return - weightedNormalStress * coefficientOfFriction(V);
  }

  double second_deriv(double V) const override {
    return 0;
  }

  double regularity(double V) const override {
podlesny's avatar
podlesny committed
    if (std::abs(V) < 1e-7) // TODO
podlesny's avatar
podlesny committed
        return std::numeric_limits<double>::infinity();

    return std::abs(second_deriv(V));
  }

  double evaluate(double V) const override {
podlesny's avatar
podlesny committed
      return - weightedNormalStress * fd.mu0 * V;
  }

  void updateAlpha(double alpha) override {}

private:
  FrictionData const fd;
  double const weightedNormalStress;
};

class ZeroFunction : public FrictionPotential {
podlesny's avatar
.  
podlesny committed
  template <typename... Args>
  ZeroFunction(Args... args) {}

Elias Pipping's avatar
Elias Pipping committed
  double evaluate(double) const override { return 0; }
Elias Pipping's avatar
Elias Pipping committed
  double coefficientOfFriction(double s) const override { return 0; }
Elias Pipping's avatar
Elias Pipping committed
  double differential(double) const override { return 0; }
Elias Pipping's avatar
Elias Pipping committed
  double second_deriv(double) const override { return 0; }
Elias Pipping's avatar
Elias Pipping committed

Elias Pipping's avatar
Elias Pipping committed
  double regularity(double) const override { return 0; }
Elias Pipping's avatar
Elias Pipping committed
  void updateAlpha(double) override {}
Elias Pipping's avatar
Elias Pipping committed
#endif