Subtracting Objects
Part of the Object Oriented Programming section of Coddy's Lua journey — lesson 27 of 70.
Just like __add handles the + operator, the __sub metamethod defines behavior for the - operator. The pattern is identical—you define a function that receives two operands and returns a new object.
local Color = {}
Color.__index = Color
function Color:new(r, g, b)
local obj = {r = r, g = g, b = b}
setmetatable(obj, Color)
return obj
end
function Color.__sub(c1, c2)
return Color:new(c1.r - c2.r, c1.g - c2.g, c1.b - c2.b)
endWhen working with RGB colors, subtraction can produce negative values. In real applications, you might want to clamp results to valid ranges (0-255), but the core metamethod structure remains the same.
local bright = Color:new(200, 150, 100)
local dim = Color:new(50, 30, 20)
local result = bright - dim
print(result.r, result.g, result.b) -- Output: 150 120 80Remember: define __sub with a dot (not colon) since it's a metamethod that Lua calls directly with both operands as arguments.
Challenge
EasyLet's build a Color class that supports subtraction using the - operator. Colors are represented by RGB values, and subtracting one color from another creates a new color with the difference of each component.
You'll organize your code across two files:
Color.lua: Define your Color class withr,g, andbcomponents representing red, green, and blue values. Include a:new(r, g, b)constructor and implement the__submetamethod so that subtracting two colors creates a new color with the component-wise differences. Remember that__subuses dot syntax and receives both operands as arguments.main.lua: Require your Color module, create color instances from the provided inputs, subtract them, and display the resulting RGB values.
You will receive six inputs:
- First color's red component
- First color's green component
- First color's blue component
- Second color's red component
- Second color's green component
- Second color's blue component
In your main file, create two colors with the given RGB values, subtract the second color from the first using the - operator, and print the resulting color's r, g, and b values on separate lines.
For example, if the inputs are 200, 150, 100, 50, 30, 20, the output should be:
150
120
80The first color (200, 150, 100) minus the second color (50, 30, 20) equals a new color (150, 120, 80).
Cheat sheet
The __sub metamethod defines behavior for the - operator. It receives two operands and returns a new object.
function Color.__sub(c1, c2)
return Color:new(c1.r - c2.r, c1.g - c2.g, c1.b - c2.b)
endDefine __sub with a dot (not colon) since it's a metamethod that Lua calls directly with both operands as arguments.
local bright = Color:new(200, 150, 100)
local dim = Color:new(50, 30, 20)
local result = bright - dim
print(result.r, result.g, result.b) -- Output: 150 120 80Try it yourself
-- Require the Color module
local Color = require('Color')
-- Read input values
local r1 = tonumber(io.read())
local g1 = tonumber(io.read())
local b1 = tonumber(io.read())
local r2 = tonumber(io.read())
local g2 = tonumber(io.read())
local b2 = tonumber(io.read())
-- TODO: Create two Color instances with the given RGB values
-- TODO: Subtract the second color from the first using the - operator
-- TODO: Print the resulting color's r, g, and b values on separate lines
This lesson includes a short quiz. Start the lesson to answer it and track your progress.
All lessons in Object Oriented Programming
1The 'Self' Concept
Tables with FunctionsExplicit 'self'The Colon SyntaxDot vs ColonRecap - Moving Point4Project: Digital Bank
Project SetupDeposit Method7Polymorphism & Overriding
Overriding MethodsCalling Parent MethodsDuck TypingCommon InterfaceChecking TypeRecap - Employee Roles10Project: Shape Manager
Project SetupRectangle Class2Class Prototype Pattern
The Prototype ConceptLinking with __indexThe :new() ConstructorInitializing AttributesIndependent InstancesRecap - Car Factory5Operator Overloading in OOP
Adding ObjectsSubtracting ObjectsConcatenating ObjectsComparing Objects (<, >)Recap - Wallet Math8Encapsulation
Naming ConventionsClosures for PrivacyAccess via ClosuresRead-Only TablesValidation LogicRecap - Secure Vault11Design Patterns (Lite)
Factory FunctionsSingleton TableIterator PatternObserver (Listener)Recap - Logger Factory3Object State and Behavior
Instance VariablesGetter MethodsSetter MethodsCalculated PropertiesFormatting StringsEquality ChecksRecap - Student Grade6Inheritance Basics
The Inheritance SetupInheriting MethodsExtending the ConstructorAdding Child MethodsShared vs UniqueRecap - Shape Hierarchy