Class: RemLint::Rules::SatisfyConstraint

Inherits:
RemLint::Rule show all
Defined in:
lib/remlint/rules/satisfy_constraint.rb

Overview

SATISFY expressions that belong in the trigger.

SATISFY works by trial: Remind proposes a date, evaluates the expression, and moves on a day if it comes back false. Anything the trigger could have pinned down instead is therefore paid for once per candidate date rather than once.

Chapter 7 measures it. Over 100,000 runs the all-SATISFY form evaluates the expression 13,214,377 times and takes 2.30s; moving the day into the trigger drops that to 482,026 evaluations and 0.58s. Same reminder, four times the speed, and the edit is mechanical:

REM SATISFY [$Td == 13 && $Tw == 5]     ->  REM 13 SATISFY [$Tw == 5]

Three trigger components can be hoisted, and each is reported only when it is compared with == against a literal, which is the form that translates directly into the trigger:

$Td  the day of the month
$Tm  the month
$Ty  the year

Two further faults share the same walk. A constraint no date can satisfy -- $Td == 100 -- costs $MaxSatIter iterations and then prints Can't compute trigger. And a $Ty < term is an UNTIL written the expensive way, which the book calls bad practice for the same reason.

Constant Summary collapse

HOISTABLE =

The trigger components a trigger can express directly, and the clause each becomes.

{
  "Td" => "a day",
  "Tm" => "a month",
  "Ty" => "a year",
}.freeze
RANGES =
{
  "Td" => (1..31),
  "Tm" => (1..12),
  "Ty" => (1990..5990),
}.freeze
COMPARISON =

$Td == 13 and $Ty < 2029, as they arrive from the lexer.

/\$(?<name>T[dmy])\s*(?<operator><=|>=|==|!=|<|>)\s*(?<value>\d+)/

Constants inherited from RemLint::Rule

RemLint::Rule::REGISTRY

Instance Attribute Summary

Attributes inherited from RemLint::Rule

#config, #document, #offenses

Class Method Summary collapse

Instance Method Summary collapse

Methods inherited from RemLint::Rule

all, find, inherited, #initialize, rule_name, #rule_name, #run

Constructor Details

This class inherits a constructor from RemLint::Rule

Class Method Details

.default_severityObject



55
56
57
# File 'lib/remlint/rules/satisfy_constraint.rb', line 55

def self.default_severity
  "info"
end

.descriptionObject



59
60
61
# File 'lib/remlint/rules/satisfy_constraint.rb', line 59

def self.description
  "A SATISFY constraint the trigger could express, or that no date satisfies."
end

.enabled_by_default?Boolean

Returns:

  • (Boolean)


51
52
53
# File 'lib/remlint/rules/satisfy_constraint.rb', line 51

def self.enabled_by_default?
  false
end

Instance Method Details

#checkObject



63
64
65
66
67
68
69
70
71
# File 'lib/remlint/rules/satisfy_constraint.rb', line 63

def check
  document.code_commands.each do |command|
    trigger = document.trigger_for(command)

    if trigger.body&.name == "SATISFY"
      check_satisfy(command, trigger)
    end
  end
end