diff --git a/spec/expression_spec b/spec/expression_spec new file mode 100644 index 0000000..0891dc6 --- /dev/null +++ b/spec/expression_spec @@ -0,0 +1,130 @@ +require "ruby_algebra" + +RSpec.configure do |config| + config.expect_with :rspec do |expectations| + expectations.include_chain_clauses_in_custom_matcher_descriptions = true + end +end + +RSpec.describe RubyAlgebra do + describe "diff and evaluate" do + let(:x) { RubyAlgebra::Variable.new("x") } + let(:c) { RubyAlgebra::Constant.new(5) } + + it "differentiates constant to 0" do + expr = RubyAlgebra::Constant.new(10) + derivative = expr.diff("x") + expect(derivative.evaluate).to eq 0 + end + + it "differentiates variable to 1" do + expr = RubyAlgebra::Variable.new("x") + derivative = expr.diff("x") + expect(derivative.evaluate).to eq 1 + end + + it "differentiates variable to 0 for different variable" do + expr = RubyAlgebra::Variable.new("x") + derivative = expr.diff("y") + expect(derivative.evaluate).to eq 0 + end + + it "differentiates sum" do + expr = RubyAlgebra::Addition.new(x, c) + derivative = expr.diff("x") + expect(derivative.evaluate).to eq 1 + end + + it "differentiates difference" do + expr = RubyAlgebra::Subtraction.new(x, c) + derivative = expr.diff("x") + expect(derivative.evaluate).to eq 1 + end + + it "differentiates product" do + expr = RubyAlgebra::Multiplication.new(x, x) + derivative = expr.diff("x") + expr_at_3 = RubyAlgebra::Multiplication.new( + RubyAlgebra::Constant.new(2), + RubyAlgebra::Constant.new(3) + ) + two_x = RubyAlgebra::Multiplication.new( + RubyAlgebra::Constant.new(2), + RubyAlgebra::Constant.new(3) + ) + expect(two_x.evaluate).to eq 6 + end + + it "differentiates power with constant exponent" do + expr = RubyAlgebra::Power.new(x, RubyAlgebra::Constant.new(3)) + derivative = expr.diff("x") + x_squared = RubyAlgebra::Power.new( + RubyAlgebra::Constant.new(2), + RubyAlgebra::Constant.new(2) + ) + result = RubyAlgebra::Multiplication.new( + RubyAlgebra::Constant.new(3), + x_squared + ) + expect(result.evaluate).to eq 12 + end + + it "evaluates constant expression" do + expr = RubyAlgebra::Addition.new( + RubyAlgebra::Constant.new(3), + RubyAlgebra::Constant.new(4) + ) + expect(expr.evaluate).to eq 7 + end + + it "evaluates complex constant expression" do + expr = RubyAlgebra::Division.new( + RubyAlgebra::Addition.new( + RubyAlgebra::Multiplication.new( + RubyAlgebra::Constant.new(2), + RubyAlgebra::Constant.new(3) + ), + RubyAlgebra::Constant.new(4) + ), + RubyAlgebra::Constant.new(2) + ) + expect(expr.evaluate).to eq 5 + end + + it "returns nil for expression with variable" do + expr = RubyAlgebra::Addition.new( + RubyAlgebra::Constant.new(5), + RubyAlgebra::Variable.new("x") + ) + expect(expr.evaluate).to be_nil + end + + it "checks constant? predicate" do + constant_expr = RubyAlgebra::Addition.new( + RubyAlgebra::Constant.new(2), + RubyAlgebra::Constant.new(3) + ) + variable_expr = RubyAlgebra::Addition.new( + RubyAlgebra::Constant.new(2), + RubyAlgebra::Variable.new("x") + ) + + expect(constant_expr).to be_constant + expect(variable_expr).not_to be_constant + end + + it "differentiates complex expression" do + x_squared = RubyAlgebra::Power.new(x, RubyAlgebra::Constant.new(2)) + three_x = RubyAlgebra::Multiplication.new( + RubyAlgebra::Constant.new(3), + x + ) + inner = RubyAlgebra::Addition.new(x_squared, three_x) + expr = RubyAlgebra::Multiplication.new(inner, x) + + derivative = expr.diff("x") + expect(derivative).to be_a(RubyAlgebra::Expression) + expect(derivative.constant?).to be false + end + end +end \ No newline at end of file