decrease file retrieving time
All checks were successful
Linux arm64 / Build (push) Successful in 2m29s

This commit is contained in:
2025-07-20 21:08:36 +02:00
parent 72e9f420ab
commit a3ef52c7a1
5 changed files with 45 additions and 67 deletions

View File

@@ -9,7 +9,7 @@
#include <string>
Piece::Piece(const Polyomino& polyomino, Block blockType) :
Piece::Piece(Polyomino&& polyomino, Block blockType) :
polyomino(polyomino),
blockType(blockType),
rotationState(NONE),

View File

@@ -22,7 +22,7 @@ class Piece {
/**
* Creates a piece with a specified shape and block type
*/
Piece(const Polyomino& piece, Block blockType);
Piece(Polyomino&& piece, Block blockType);
/**
* Rotates the piece in the specified direction

View File

@@ -50,11 +50,12 @@ bool PiecesFiles::savePieces(int polyominoSize, std::vector<Polyomino>& polyomin
std::uint8_t infoByte = (isConvex << 7) + (hasHole << 6) + polyomino.getLength();
buffer << infoByte;
const int bitsNeeded = polyomino.getLength() * polyomino.getLength();
const int longsNeeded = bitsNeeded / 64 + 1;
// write the positions of the piece
std::uint8_t positionByte;
for (const Position position : polyomino.getPositions()) {
positionByte = (position.x << 4) + position.y;
buffer << positionByte;
for (int i = 0; i < longsNeeded; i++) {
buffer << polyomino.getPositionsData()[i];
}
}
@@ -91,11 +92,11 @@ bool PiecesFiles::loadPieces(int polyominoSize, std::vector<Piece>& pieces, std:
nextPieceBlockType(pieceBlock);
}
char convexMask = 0b1000'0000;
char holeMask = 0b0100'0000;
char lengthMask = 0b0011'1111;
char xMask = 0b1111'0000;
char yMask = 0b0000'1111;
constexpr char convexMask = 0b1000'0000;
constexpr char holeMask = 0b0100'0000;
constexpr char lengthMask = 0b0011'1111;
constexpr char xMask = 0b1111'0000;
constexpr char yMask = 0b0000'1111;
std::uint8_t infoByte;
int i = 0;
@@ -108,18 +109,17 @@ bool PiecesFiles::loadPieces(int polyominoSize, std::vector<Piece>& pieces, std:
bool hasHole = (infoByte & holeMask) >> 6;
int length = (infoByte & lengthMask);
const int bitsNeeded = length * length;
const int longsNeeded = bitsNeeded / 64 + 1;
// read positions
std::set<Position> piecePositions;
std::uint8_t positionByte;
for (int i = 0; i < polyominoSize; i++) {
buffer >> positionByte;
int x = ((unsigned char) positionByte & xMask) >> 4;
int y = positionByte & yMask;
piecePositions.insert(Position(x, y));
Polyomino::PolyominoData polyominoData{};
for (int i = 0; i < longsNeeded; i++) {
buffer >> polyominoData[i];
}
// create piece
Piece readPiece(Polyomino(std::move(piecePositions), length), pieceBlock);
Piece readPiece(Polyomino(std::move(polyominoData), length), pieceBlock);
nextPieceBlockType(pieceBlock);
pieces.push_back(readPiece);

View File

@@ -31,38 +31,6 @@ Polyomino::Polyomino(std::set<Position>&& positions) {
this->positions = std::move(temp.positions);
}
Polyomino::Polyomino(std::set<Position>&& positions, std::int8_t length) : positions(), length(length){
for (Position position : positions) {
insert(position);
}
}
Polyomino::Polyomino(PolyominoData&& positions) : positions(positions) {
int minX = INT_MAX;
int maxX = INT_MIN;
int minY = INT_MAX;
int maxY = INT_MIN;
// tout s'appelle positions, osekour !
std::vector<Position> tempPositions = getPositions();
for (const Position position : tempPositions) {
if (position.x < minX) minX = position.x;
if (position.x > maxX) maxX = position.x;
if (position.y < minY) minY = position.y;
if (position.y > maxY) maxY = position.y;
}
this->length = std::max(maxX - minX + 1, maxY - minY + 1);
// we normalize here instead of calling this->normalize() to reduce the number of calculations for the generation algorithm
Polyomino temp(PolyominoData{}, this->length);
for (Position position : tempPositions) {
temp.insert(Position(position.x - minX, position.y - minY));
}
this->positions = std::move(temp.positions);
}
Polyomino::Polyomino(PolyominoData&& positions, std::int8_t length) :
positions(std::move(positions)),
length(length) {
@@ -79,7 +47,7 @@ void Polyomino::normalize() {
if (position.y < minY) minY = position.y;
}
Polyomino temp(PolyominoData{}, this->length);
Polyomino temp({}, this->length);
for (const Position position : tempPositions) {
temp.insert(Position(position.x - minX, position.y - minY));
}
@@ -87,7 +55,7 @@ void Polyomino::normalize() {
}
void Polyomino::rotateCW() {
Polyomino temp(PolyominoData{}, this->length);
Polyomino temp({}, this->length);
for (const Position position : getPositions()) {
temp.insert(Position(position.y, (length - 1) - (position.x)));
}
@@ -95,7 +63,7 @@ void Polyomino::rotateCW() {
}
void Polyomino::rotate180() {
Polyomino temp(PolyominoData{}, this->length);
Polyomino temp({}, this->length);
for (const Position position : getPositions()) {
temp.insert(Position((length - 1) - (position.x), (length - 1) - (position.y)));
}
@@ -103,7 +71,7 @@ void Polyomino::rotate180() {
}
void Polyomino::rotateCCW() {
Polyomino temp(PolyominoData{}, this->length);
Polyomino temp({}, this->length);
for (const Position position : getPositions()) {
temp.insert(Position((length - 1) - (position.y), position.x));
}
@@ -200,7 +168,7 @@ void Polyomino::goToSpawnPosition() {
}
// center the piece with an up bias
Polyomino temp(PolyominoData{}, this->length);
Polyomino temp({}, this->length);
for (const Position position : tempPositions) {
temp.insert(Position((position.x - minX) + (verticalEmptyLines / 2), (position.y - minY) + ((horizontalEmptyLines + 1) / 2)));
}
@@ -298,7 +266,7 @@ void Polyomino::tryToInsertPosition(std::set<Position>& emptyPositions, const Po
tryToInsertPosition(emptyPositions, Position(candidate.x - 1, candidate.y));
}
const PolyominoData& Polyomino::getPositionsData() const {
const Polyomino::PolyominoData& Polyomino::getPositionsData() const {
return this->positions;
}
@@ -369,3 +337,10 @@ void Polyomino::insert(const Position& position) {
int bitIndex = posIndex % (sizeof(std::uint64_t) * 8);
this->positions[longIndex] |= static_cast<std::uint64_t>(1) << (sizeof(std::uint64_t) * 8 - bitIndex);
}
void Polyomino::erase(const Position& position) {
int posIndex = position.y * this->length + position.x;
int longIndex = posIndex / (sizeof(std::uint64_t) * 8);
int bitIndex = posIndex % (sizeof(std::uint64_t) * 8);
this->positions[longIndex] &= ~(static_cast<std::uint64_t>(1) << (sizeof(std::uint64_t) * 8 - bitIndex));
}

View File

@@ -7,30 +7,29 @@
#include <iostream>
#include <array>
using PolyominoData = std::array<std::uint64_t, 4>;
/**
* A mathematical object consisting of touching squares on a 2D grid
*/
class Polyomino {
public:
static const std::size_t POLYOMINO_DATA_SIZE = 4;
using PolyominoData = std::array<std::uint64_t, POLYOMINO_DATA_SIZE>;
private:
PolyominoData positions; // the squares composing the polyomino, stored in binary. MSB is downleft
std::int8_t length; // the size of the smallest square box in which the polyomino can fit on any rotation
public:
/**
* Creates a polyomino with the specified positions and normalizes it, wheter it is actually a polyonimo is not checked
*/
Polyomino(PolyominoData&& positions);
/**
* Creates a polyomino with the specified positions and length, wheter it is actually a polyonimo of this length is not checked
*/
Polyomino(PolyominoData&& positions, std::int8_t length);
// this is temporary. They are here for compatibility reasons for now
/**
* Creates a polyomino with the specified positions and normalizes it, wheter it is actually a polyonimo is not checked
*/
Polyomino(std::set<Position>&& positions);
Polyomino(std::set<Position>&& positions, std::int8_t length);
/**
* Translates the polyomino to the lowest unsigned values (lower row on y = 0, and left-most column on x = 0)
@@ -127,9 +126,13 @@ class Polyomino {
*/
bool contains(const Position& position) const;
private:
/**
* @brief Insert a square at the position
*/
void insert(const Position& position);
/**
* @brief Removes a square at the position
*/
void erase(const Position& position);
};