Du må være registrert og logget inn for å kunne legge ut innlegg på freak.no
X
LOGG INN
... eller du kan registrere deg nå
Dette nettstedet er avhengig av annonseinntekter for å holde driften og videre utvikling igang. Vi liker ikke reklame heller, men alternativene er ikke mange. Vær snill å vurder å slå av annonseblokkering, eller å abonnere på en reklamefri utgave av nettstedet.
  7 2451
Nedenfor er et firkant på 5x5 pixler definert radvis som RGB-variabler i Python:
colorsRow1 = [(0,0,0), (175,10,10), (175,10,10), (175,10,10), (0,0,0)]
colorsRow2 = [(10,160,170),(0,0,0),(175,10,10),(0,0,0),(10,160,170)]
colorsRow3 = [(10,160,170), (10,160,170), (0,0,0), (10,160,170), (10,160,170)]
colorsRow4 = [(10,160,170), (0,0,0), (175,10,10), (0,0,0), (10,160,170)]
colorsRow5 = [(0,0,0),(175,10,10),(175,10,10),(175,10,10),(0,0,0)]

Her er resultatet som et bilde (5x5 pixler definert radvis):


Spørsmål:
Det jeg ønsker å gjøre er å finne og ventuelt returnere posisjonene på pixelsamlingen fra et bilde. Jeg vet at det finnes libraries hvor man kan finne bilder i bilder, men da må jeg ha bildene den skal lagre som faktiske bilder. Jeg vil gjerne ha de lagret som tekst. Det første som falt meg inn bare å bruteforce søke igjennom alle pixler med like farger, for så å gjøre nødvendige sjekker for å finne ut om de matcher. Men jeg er på jakt etter bedre, billigere og mer elegante løsninger for dette, noe som har noen forslag?
Jeg skjønte ikke spørsmålet. Hva er en pikselsamling? Og hva mener du med å finne bilder i bilder? Hva er bruksområdet for dette? Det er nok enklere å hjelpe om du forteller mer.
Sist endret av Ozma; 7. juni 2018 kl. 23:48.
Vel, bilder består jo av pixler, i et høyoppløslig bilde på f.eks. (1920x1080) så tilsvarer dette 2073600 pixler. Jeg har et sett med 10 pixler jeg ønsker å finne ut om eksisterer i et eksempebilde, men i og med at det er så utrolig mange pixler så er jeg usikker på hvordan jeg raskest mulig kan fikke ut om "mine" pixler i andre bilder.
Det er ikke et alternativ å for-loope gjennom hele bildet?
Ah, sånn ja. Jeg tror ikke det finnes noen metoder med raskere kjøretid enn bruteforce-metoden som du nevnte.

Eksempelkode:

https://stackoverflow.com/questions/...ge-recognition

Hvis det er for tregt med NumPy, sjekk ut Cython, Numba, CUDA, etc, etc. Koden må kompileres til maskinkode og kjøres parallelt på CPU eller GPU. (Selv om jeg mistenker at CPU er raskere i dette tilfellet fordi "sub-bildet" (kernelen) er såpass liten.
Limited edition
Moff's Avatar
Den raskeste måten jeg kan klare å komme opp med er at du prøver å finne alle pixler med én av verdiene du leter etter. Ta den mest "unormale" pixelen du leter etter og gå gjennom hele bildet for å se hvor mange slike pixler som finnes. Sannsynligheten for å finne en syregrønn pixel er vesentlig lavere enn enn sannsynligheten for å finne en svart eller hvit pixel, så det er derfor lurt å velge noe som er litt unormalt.

Når du har funnet alle posisjoner med denne éne pixelen, så kan du begynne med eliminering. Først ser du om pixelen er plassert på en slik måte at det er mulig at det er den du leter etter. For eksempel, hvis pixelen du har funnet er helt til høyre i bildet du leter i, men ikke er helt til høyre i bildet du leter etter, så kan det umulig være en match. Når du har eliminert alle posisjoner som ikke kan være en match, så kan du begynne med pixel-for-pixel-sammenligning til du er 100% sikker på at du har funnet mønsteret ditt.

I korte trekk: Det er raskere å finne ut om mønsteret ikke er der, enn å finne ut om det er der.

Med det sagt så trenger du et ting til, og det er en eller annen form for komprimering av bildet du søker i. Når du søker pixel-for-pixel så vil du få et problem i det øyeblikket bildet du søker i har blitt forstørret eller redusert, rotert, gjort speilvendt eller noen har tuklet med fargene i det. Hvis alle pixler har blitt gjort 0,01% lysere enn de var originalt, hvordan klarer du å fange opp dette? Hvis bildet har blitt lagret som JPG eller et annet "lossy"-format, så vil du typisk få artifacts som påvirker fargene også.

Det er absolutt mulig å løse, men alt er avhengig av hvor nøyaktig du ønsker eller trenger å være.
Det finnes en del optimaliseringer du kan gjøre, både probabilistiske og heuristiske. Det kommer veldig an på hvilke typer mønster du ser etter. Er det alltid kvadratiske, symmetriske, <=3-fargede mønstre? Eller må du støtte rektangulære klosser med hele RGB-spekteret?

Hvis du kan anta at mønsteret har svært få farger, og er av en viss størrelse, så kan du hoppe like langt som mønsteret er langt, og så sjekke om pixelen matcher en farge som er i mønsteret ditt. Dette reduserer søkerommet ditt betraktelig, gitt at antall farger er mindre enn dimensjonen på mønsteret. Du kan så sjekke alle interessante pixel-områder i etterkant, sortert etter hvor "sjelden" den fargen du fant er - slik som Moff nevner over.

Hvis mønsteret er slik at det alltid stikker seg veldig ut på bildet, enten pga. harde kanter, farger som ikke matcher bakgrunnen osv. så har du også en del metoder. Det du ønsker å gjøre da går under "Image Segmentation", som har et utall forskjellige fremgangsmåter: Region-growing, edge detection, rekursive histogram-analyser, og clustering for å nevne noen.

Et annet alternativ, om du ikke nødvendigvis ser etter effektive algoritmer, er å bruke PIL/Pillow til å lagre mønsteret ditt som et bilde. Da kan du bruke bedre verktøy som OpenCV o.l. til å finne mønstrene. Dette er ofte tusen ganger enklere hvis du skal gjenkjenne mønstre som plutselig kan være på skrå, opp-ned, zoomet inn på osv. i bildet du søker i.
sindre@puse.cat:~$
Synderen's Avatar
Om det er maskin genererte bilder med mønstre, og ikke et naturlig bilde så kan jeg tenke meg at søk med Aho–Corasick kan være effektivt. Med litt fikling kan du gjøre det med Snort/Suricata , og da bruke regel motorene de har til å enkelt definere mønstre du leter etter. Dette kan kun brukes om du leter etter spesifikke pixel verdier. Det vil ikke funke for å gjenkjenne mønstre fra bilder som er tatt med et kamera.