From e234ed2a107724de263ba1b28fd7092570106606 Mon Sep 17 00:00:00 2001 From: Fawkes100 Date: Wed, 11 Dec 2024 21:35:13 +0100 Subject: [PATCH] Day 6: Part 2 --- Aufgabe 5/main.cpp | 1 + Aufgabe 6/CMakeLists.txt | 4 ++ Aufgabe 6/main.cpp | 90 +++++++++++++++++++++++++++++++++++++++- 3 files changed, 94 insertions(+), 1 deletion(-) diff --git a/Aufgabe 5/main.cpp b/Aufgabe 5/main.cpp index 1d9f9a6..e326597 100644 --- a/Aufgabe 5/main.cpp +++ b/Aufgabe 5/main.cpp @@ -4,6 +4,7 @@ #include #include #include +#include struct Rule{ diff --git a/Aufgabe 6/CMakeLists.txt b/Aufgabe 6/CMakeLists.txt index c2425e8..1e0f6f2 100644 --- a/Aufgabe 6/CMakeLists.txt +++ b/Aufgabe 6/CMakeLists.txt @@ -4,3 +4,7 @@ project(Aufgabe_6) set(CMAKE_CXX_STANDARD 17) add_executable(Aufgabe_6 main.cpp) +find_package(OpenMP REQUIRED) +if (OpenMP_CXX_FOUND) + target_link_libraries(Aufgabe_6 OpenMP::OpenMP_CXX) +endif() diff --git a/Aufgabe 6/main.cpp b/Aufgabe 6/main.cpp index 00001ae..52a8459 100644 --- a/Aufgabe 6/main.cpp +++ b/Aufgabe 6/main.cpp @@ -1,6 +1,7 @@ #include #include #include +#include struct Point { int x; @@ -97,7 +98,8 @@ bool hasGuardReachedObstacle(Point guardPosition, const std::vector& map) return false; } -std::vector calcGuardPositions(Guard& guard, const std::vector& map, int mapSizeX, int mapSizeY) { + +std::vector calcGuardPositions(Guard guard, const std::vector& map, int mapSizeX, int mapSizeY) { std::vector guardPositions; while(guard.currentPosition.isValid(mapSizeX, mapSizeY)) { bool duplicated = false; @@ -121,7 +123,90 @@ std::vector calcGuardPositions(Guard& guard, const std::vector& ma return guardPositions; } +/**std::vector calcObstaclePositionForCycle(Guard initialGuard, const std::vector& map, int mapSizeX, int mapSizeY) { + Guard guard = initialGuard; + std::vector possibleObstaclePositions; + + #pragma omp parallel + // Lokaler Vector für jeden Thread + std::vector localObstaclePositions; + for(int x=0; x < mapSizeX; x++) { + #pragma omp for collapse(2) schedule(dynamic) + for(int y =0; y < mapSizeY; y++) { + Guard localGuard = guard; + std::vector guardPositions; + std::vector currentMap = map; + currentMap.emplace_back(x, y); + while(localGuard.currentPosition.isValid(mapSizeX, mapSizeY)) { + guardPositions.push_back(guard.currentPosition); + + if(guardPositions.size() > (mapSizeX * mapSizeY)) { + localObstaclePositions.emplace_back(x, y); + break; + } + + Point nextPosition = calcUpdatedGuardPosition(localGuard.currentPosition, localGuard.currentDirection); + if(hasGuardReachedObstacle(nextPosition, currentMap)) { + localGuard.currentDirection = static_cast((localGuard.currentDirection + 1) % 4); + } else { + localGuard.currentPosition = nextPosition; + } + } + guard = initialGuard; + } + } + // Zusammenführen der lokalen Ergebnisse in den globalen Vector + #pragma omp critical + possibleObstaclePositions.insert(possibleObstaclePositions.end(), localObstaclePositions.begin(), localObstaclePositions.end()); + return possibleObstaclePositions; +}**/ + +std::vector calculateObstaclePositions(Guard initialGuard, std::vector map, int mapSizeX, int mapSizeY) { + Guard guard = initialGuard; + std::vector possibleObstaclePositions; + + // OpenMP für Parallelisierung der äußeren Schleife +#pragma omp parallel + { + // Lokaler Vector für jeden Thread + std::vector localObstaclePositions; + +#pragma omp for collapse(2) schedule(dynamic) + for (int x = 0; x < mapSizeX; x++) { + for (int y = 0; y < mapSizeY; y++) { + Guard localGuard = guard; // Kopie des Guards für jeden Thread + std::vector guardPositions; + std::vector currentMap = map; // Lokale Kopie der Karte + currentMap.emplace_back(x, y); + + while (localGuard.currentPosition.isValid(mapSizeX, mapSizeY)) { + guardPositions.push_back(localGuard.currentPosition); + + if (guardPositions.size() > (mapSizeX * mapSizeY)) { + localObstaclePositions.emplace_back(x, y); + break; + } + + Point nextPosition = calcUpdatedGuardPosition(localGuard.currentPosition, localGuard.currentDirection); + if (hasGuardReachedObstacle(nextPosition, currentMap)) { + localGuard.currentDirection = static_cast((localGuard.currentDirection + 1) % 4); + } else { + localGuard.currentPosition = nextPosition; + } + } + } + } + + // Zusammenführen der lokalen Ergebnisse in den globalen Vector +#pragma omp critical + possibleObstaclePositions.insert(possibleObstaclePositions.end(), localObstaclePositions.begin(), localObstaclePositions.end()); + } + + return possibleObstaclePositions; +} + int main() { + std::vector input = readTextFromFile("../input.txt"); Point initialGuardPos = calcGuardPositionFromInput(input); std::vector obstaclePositions = calcObstaclePositionsFromInput(input); @@ -129,5 +214,8 @@ int main() { auto visitedPoints = calcGuardPositions(guard, obstaclePositions, input[0].size(), input.size()); std::cout << "The guard visited " << visitedPoints.size() << " points!" << std::endl; + + auto possibleObstaclePositions = calculateObstaclePositions(guard, obstaclePositions, input[0].size(), input.size()); + std::cout << "There are " << possibleObstaclePositions.size() << " possible positions!" << std::endl; return 0; }