CS 330 Lecture 24 – Generics/templates
Agenda
- named constructor pattern
- typing: strong and static and dynamic
- a peril of static typing: code
- Java generics
- C++ templates
TODO
Code
makefile
drawer: drawer.cpp Vector.h Matrix.h Matrix.cpp Vector.cpp g++ -Wall -o drawer Vector.cpp Matrix.cpp drawer.cpp
Vector.cpp
#include <cassert> #include "Vector.h" Vector2::Vector2() : x(0.0f), y(0.0f) { } Vector2::Vector2(float x, float y) : x(x), y(y) { } float& Vector2::operator[](int index) { assert(index >= 0 && index <= 1); return index == 0 ? x : y; } const float& Vector2::operator[](int index) const { assert(index >= 0 && index <= 1); return index == 0 ? x : y; } Vector2 Vector2::operator+(const Vector2& other) { return Vector2(x + other.x, y + other.y); } std::ostream& operator<<(std::ostream& out, const Vector2& v) { out << v[0] << "," << v[1]; return out; }
Vector.h
#ifndef VECTOR_H #define VECTOR_H #include <iostream> #include <fstream> class Vector2 { public: Vector2(); Vector2(float x, float y); // write a subscript operator float& operator[](int index); const float& operator[](int index) const; Vector2 operator+(const Vector2& other); // overload a print operator private: float x; float y; }; std::ostream& operator<<(std::ostream& out, const Vector2& v); #endif
Matrix.cpp
#include <cmath> #include "Matrix.h" Matrix2::Matrix2() { } float& Matrix2::operator()(int r, int c) { return elements[r * 3 + c]; } const float& Matrix2::operator()(int r, int c) const { return elements[r * 3 + c]; } Vector2 operator*(const Matrix2& m, const Vector2& v) { Vector2 product; // dot m's row 0 with v's col 0 product[0] = m(0, 0) * v[0] + m(0, 1) * v[1] + m(0, 2); // dot m's row 1 with v's col 0 product[1] = m(1, 0) * v[0] + m(1, 1) * v[1] + m(1, 2); return product; } Matrix2 Matrix2::GetScale(float x, float y) { Matrix2 m; m(0, 0) = x; m(1, 1) = y; m(2, 2) = 1.0f; m(0, 1) = m(0, 2) = m(1, 0) = m(1, 2) = m(2, 0) = m(2, 1) = 0.0f; return m; } Matrix2 Matrix2::GetRotate(float degrees) { float radians = degrees * 3.14159f / 180.0f; Matrix2 m; m(0, 0) = cos(radians); m(0, 1) = -sin(radians); m(1, 1) = cos(radians); m(1, 0) = sin(radians); m(2, 2) = 1.0f; m(0, 2) = m(1, 2) = m(2, 0) = m(2, 1) = 0.0f; return m; } /* ------------------------------------------------------------------------- */
Matrix.h
#ifndef MATRIX_H #define MATRIX_H #include "Vector.h" class Matrix2 { public: Matrix2(); float& operator()(int r, int c); const float& operator()(int r, int c) const; static Matrix2 GetScale(float x, float y); static Matrix2 GetRotate(float degrees); static Matrix2 GetTranslate(float x, float y); private: /* float elements[9]; */ double elements[9]; }; Vector2 operator*(const Matrix2& m, const Vector2& v); #endif
drawer.cpp
#include <cmath> #include <iostream> #include "Matrix.h" #include "Vector.h" int main() { Matrix2 rotate = Matrix2::GetRotate(30.0f); Matrix2 scale = Matrix2::GetScale(1.04f, 1.04f); /* float radians = 30.0f * 3.14159f / 180.0f; */ /* transform(0, 0) = cos(radians); */ /* transform(0, 1) = -sin(radians); */ /* transform(1, 0) = sin(radians); */ /* transform(1, 1) = cos(radians); */ /* transform(0, 2) = 0.0f; */ /* transform(1, 2) = 0.0f; */ /* transform(2, 0) = 0.0f; */ /* transform(2, 1) = 0.0f; */ /* transform(2, 2) = 1.0f; */ Vector2 point(1.0f, 0.0f); std::cout << point << std::endl; for (int i = 0; i < 120; ++i) { point = rotate * point; point = scale * point; std::cout << point << std::endl; } /* Vector2 point2(1.0f, 2.0f); */ /* Vector2 sum = point + point2; */ /* Vector2 sum = point.operator+(point2); */ /* std::cout << "sum[0]: " << sum[0] << std::endl; */ /* std::cout << "sum[1]: " << sum[1] << std::endl; */ /* std::cout << "sum: " << sum << std::endl; */ /* std::cout << "point[0]: " << point[0] << std::endl; */ /* std::cout << "point[1]: " << point[1] << std::endl; */ /* point[0] = 11.0f; */ /* std::cout << "point[0]: " << point[0] << std::endl; */ /* std::cout << "point[1]: " << point[1] << std::endl; */ /* point[0] // point.getX() */ /* point[1] // point.getY() */ }
ArrayList.java
package cs330; public class ArrayList { private Object[] stuff; private int size; public ArrayList() { stuff = new Object[10]; size = 0; } public Object get(int i) { return stuff[i]; } public int size() { return size; } public boolean add(Object o) { if (size == stuff.length) { Object[] aWholeLotMoreStuff = new Object[stuff.length * 2]; System.arraycopy(stuff, 0, aWholeLotMoreStuff, 0, stuff.length); stuff = aWholeLotMoreStuff; } stuff[size] = o; ++size; return true; } }
Haiku
on code reuse:
“Don’t reinvent the wheel!”
Ignore them. We don’t need wheels.
We need inventors.
“Don’t reinvent the wheel!”
Ignore them. We don’t need wheels.
We need inventors.