Wątek przeniesiony 2023-03-20 02:18 z C/C++ przez kq.

Porównanie kropek i linii pomiędzy obrazami

0

Nie musi to być konkretnie zrobione za pomocą c++ może to być zrobione i w innym języku tylko chciał bym dokładne wytłumaczenie jak kod uruchomić.

1.png2.png

0

Nie wiem, czy to zadziała dla takiego przypadku, ale nic nie szkodzi spróbować ;)
https://stackoverflow.com/questions/7853628/how-do-i-find-an-image-contained-within-an-image

A jakby się bardziej zastanowić, to nie byłoby zbyt trudne napisanie algorytmu, który znajduje wzorzec na zasadzie relatywnej odległości/położenia kropek i podobieństwa kolorów.

3

Co rozumiesz przez porównać ?

2
S4t napisał(a):

Co rozumiesz przez porównać ?

Decydujące pytanie. Obawiam się, że bez solidnych fundamentów z matematyki @Winter Wolfie ciezko będzie nawet wyłuszczyć zagadnienie
naiwne "porównanie na równosć" jest jak milion w totolotka, bez szans.

0

Ja rozumiem, że chcemy znaleźć ten kawałek obrazka w tej * konstelacji* ?

0

Hasło do wyszukania to "computer vision", ale to złożony temat.

Może lepiej uprościć problem i rozwiązać problem łatwiejszy / obejść go? Co chcesz osiągnąć tak naprawdę?

0

troche się zainteresowałem i ja bym startowął z visgrep oraz
compare -verbose -metric NCC -subimage-search big.png small.png dump.png
ImageMagick ^

Tylko chyba musisz poresizować swoja foteczkę small.png.

Dosyć długo to pracuje. ( taka mini podpowiedź ode mnie )

Pokombinuj też z przejściem na szarość.

1
Winter Wolfie napisał(a):

Nie musi to być konkretnie zrobione za pomocą c++ może to być zrobione i w innym języku tylko chciał bym dokładne wytłumaczenie jak kod uruchomić.

Jaki kod?

1

Bawiłem się tym i ciężko jest znaleźć stricte zależność. Znajdywałem podobne punkty ale nie w pełni odzwierciedlające poszukiwany. używając tego modułu imagemagick ale
dosyć długo to skanuje i jeszcze musiałem resizować ten mały obrazek.
Ponad to jest kilka rodzajów szukania i część daje jakieś minimalnie sensowne wyniki a część fatalne.

Takie trzy grosze ode mnie.

3

Najbardziej trafny algorytm trafił spine.

A to moje rozwinięcie algorytmu, spojrzałem na problem i widzę rozwiązanie w 6 ruchach do przodu.

Pierwsze wydaje się, że da się ten problem rozwiązać lepiej, gra ma jakiś interface, który można wykorzystać, a jak chcesz wykorzystać zwykły obraz to:
hough lines i hough circle, do określenia linii i okręgów, opowiednie parametry sprawią, że znajdziesz to co potrzebujesz.

Teraz robisz intersekcję linii z kołkami i jeśli występuje dodajesz jako krawędź do wierzchołka w grafie.
Zapamiętujesz także kolor wierzchołka, położenie wierzchołka.

Do której strony krawędzi przypniesz wierzchołek możesz wydedukować na podstawie intersekcji z którą stroną linii.

Mając wygenerowany graf, wybierasz jakiś wierzchołek patternu i wyszukujesz dany wierzchołki w grafie po kolorze.

Mając listę kolorów, sprawdzasz dla każdego znalezionego czy jego sąsiedzi zgadzają się z patternem.

Jak znajdziesz jednego lub więcej, to przy większej ilości porównujesz także kąty między poszczególnymi wierzchołkami.
Czyli zwykły vector dot produkt.

Cena zaimplementowania takiego algorytmu, a jest dosyć zaawansowany powinna być w granicach 500-1000zł może więcej, ale nie znam aktualnych cen, powinieneś to uszanować bo to za przykręcenie uszczelki skasują cię więcej, a to nawet jest trudniejsza praca.

0

Porównanie kropek i linii na obrazach może być wykonane w języku C++ z użyciem bibliotek do przetwarzania obrazów, takich jak OpenCV lub ImageMagick.
Aby porównać obrazy w OpenCV, należy użyć funkcji cv::absdiff() do wyznaczenia różnicy pikseli między dwoma obrazami. Następnie wynikowy obraz różnicowy można przetworzyć za pomocą cv::threshold() lub innych funkcji przetwarzania obrazów, aby zidentyfikować kropki lub linie.

#include <iostream>

using namespace cv;
using namespace std;

int main(int argc, char** argv)
{
    // wczytanie dwóch obrazów
    Mat img1 = imread("obraz1.jpg", IMREAD_GRAYSCALE);
    Mat img2 = imread("obraz2.jpg", IMREAD_GRAYSCALE);

    // wyznaczenie różnicy pikseli
    Mat diff;
    absdiff(img1, img2, diff);

    // binaryzacja różnicowego obrazu
    Mat thresh;
    threshold(diff, thresh, 0, 255, THRESH_BINARY);

    // wykrycie konturów
    vector<vector<Point> > contours;
    findContours(thresh, contours, RETR_LIST, CHAIN_APPROX_SIMPLE);

    // wyświetlenie liczby wykrytych konturów
    cout << "Liczba wykrytych konturów: " << contours.size() << endl;

    return 0;
}

Ten kod wczytuje dwa obrazy, wyznacza różnicę pikseli między nimi, binaryzuje wynikowy obraz różnicowy, wykrywa kontury i wyświetla liczbę wykrytych konturów.

Aby wykonać porównanie kropek i linii za pomocą ImageMagick, można użyć narzędzia "compare", które porównuje dwa obrazy i zwraca wynikowy obraz różnicowy. Można również użyć funkcji "connected-components" lub innych funkcji przetwarzania obrazów, aby zidentyfikować kropki lub linie.

Oto przykładowy kod w ImageMagick, który wykonuje porównanie kropek i linii między dwoma obrazami:

#include <iostream>

using namespace std;
using namespace Magick;

int main(int argc, char** argv)
{
    // wczytanie dwóch obrazów
    Image img1("obraz1.jpg");
    Image img2("obraz2.jpg");

    // wyznaczenie różnicy pikseli
    Image diff;
    diff = img1;
    diff.compare(img2);

    // wykrycie kropek i linii
    diff.connectedComponents();

    // wyświetlenie liczby kropek i linii
    cout << "Liczba kropek: " << diff.attribute("connected-components:area-thresholded-count") << endl;
    cout << "Liczba linii: " << diff.attribute("connected-components:mean
    ```

1 użytkowników online, w tym zalogowanych: 0, gości: 1