Video objekti tuvastamise kohta Raspberry Pi-l

Proloog

Praegu levib internetis video, kuidas Tesla autopiloot nÀeb teed.

Olen juba ammu tahtnud edastada videot, mida tÀiustatakse detektoriga, ja seda reaalses ajas.

Video objekti tuvastamise kohta Raspberry Pi-l

Probleem on selles, et tahan videot edastada Raspberry-lt, kuid nÀrvivÔrgu detektori jÔudlus on kehv.

Intel Neural Computer Stick

Olen kaalunud erinevaid lahendusi.

V eelmisel artiklil Eksperimenteerin Intel Neural Computer Stickiga. Seade on vÔimas, kuid vajab oma vÔrgu formaati.

Kuigi Intel pakub konvertereid peamiste raamistike jaoks, on siin mitmeid peidetud probleeme.

NĂ€iteks vajalik vĂ”rgu formaat vĂ”ib olla ĂŒhilduv, ja isegi kui see on ĂŒhilduv, vĂ”ivad mĂ”ned kihid seadmes ei ole toetatud, aga kui need on toetatud, vĂ”ivad konversiooni kĂ€igus tekkida vead, mille tulemuseks on mĂ”ned kummalised asjad.

ÜhesĂ”naga, kui soovite mĂ”nda suvalist nĂ€rvivĂ”rku, siis ei pruugi see NCS-iga Ă”nnestuda. SeetĂ”ttu otsustasin proovida probleemi lahendada kĂ”ige massilisemate ja kergesti juurdepÀÀsetavate tööriistade kaudu.

Pilv

Ilmselt on kohalikule riistvaralahendusele alternatiiviks ĂŒleminek pilve.

ValikuvÔimalusi on tohutult.

KÔik liidrid:


 ja kĂŒmneid vĂ€hem tuntud.

Selle mitmekesisuse seast valimine pole just lihtne.

Otsustasin mitte valida, vaid tÔsta vana hea tööprotsessi OpenCV Dockerisse ja kÀivitada see pilves.

Selle lĂ€henemise eeliseks on paindlikkus ja kontroll — saab vahetada nĂ€rvivĂ”rku, hostimist, serverit — ĂŒldiselt kĂ”ike, mida soovid.

Server

Alustame kohalikust prototĂŒĂŒbist.

Tavaliselt kasutan REST API jaoks Flaski, OpenCV-d ja MobileSSD vÔrku.

Paigaldades Dockerisse uusimad versioonid, avastasin, et OpenCV 4.1.2 ei tööta koos Mobile SSD v1_coco_2018_01_28-ga ning pidin tagasi minema tÔestatud 11_06_2017 versiooni.

Teenuse kÀivitamisel laadime klasside nimed ja vÔrgu:

def init():
    tf_labels.initLabels(dnn_conf.DNN_LABELS_PATH)
    return cv.dnn.readNetFromTensorflow(dnn_conf.DNN_PATH, dnn_conf.DNN_TXT_PATH)

Kohalikus Dockeris (mitte kĂ”ige uuemas sĂŒlearvutis) vĂ”tab see 0,3 sekundit, Raspberry-l aga 3,5.

KĂ€ivitame arvutuse:

def inference(img):
    net.setInput(cv.dnn.blobFromImage(img, 1.0/127.5, (300, 300), (127.5, 127.5, 127.5), swapRB=True, crop=False))
    return net.forward()

Docker — 0,2 sek, Raspberry — 1,7.

Muutame tensori vÀljundi loetavaks json-iks:

def build_detection(data, thr, rows, cols):
    ret = []
    for detection in data[0,0,:,:]:
        score = float(detection[2])
        if score > thr:
            cls = int(detection[1])
            a = {"class" : cls, "name" : tf_labels.getLabel(cls),  "score" : score}
            a["x"] = int(detection[3] * cols)
            a["y"] = int(detection[4] * rows)
            a["w"] = int(detection[5] * cols ) - a["x"]
            a["h"] = int(detection[6] * rows) - a["y"]
            ret.append(a)
    return ret

Edasi me eksportime selle operatsiooni lĂ€bi Flaski(sisendiks on pilt, vĂ€ljundiks — detektori tulemused json-formaadis).

Alternatiivne variant, kus rohkem tööd kantakse serveri Ă”lule: see joonistab leitud objektid ise ĂŒmber ja tagastab valmis pildi.

See variant sobib hÀsti, kui me ei soovi opencv-d serverisse tuua.

Docker

Kogume pildi.

Kood on korrastatud ja postitatud Github, docker vÔtab selle otse sealt.

Platvormiks vĂ”tame sama Debian Stretchi, mis on Raspberry peal — ei lĂ€he usaldusvÀÀrsest tehnoloogiapakist kaugemale.

Peame installima flaski, protobufi, requests'i, opencv_python'i, alla laadima Mobile SSD, serverikoodi GitHubist ja serveri kÀivitama.

FROM python:3.7-stretch

RUN pip3 install flask
RUN pip3 install protobuf
RUN pip3 install requests
RUN pip3 install opencv_python

ADD http://download.tensorflow.org/models/object_detection/ssd_mobilenet_v1_coco_11_06_2017.tar.gz /
RUN tar -xvf /ssd_mobilenet_v1_coco_11_06_2017.tar.gz

ADD https://github.com/tprlab/docker-detect/archive/master.zip /
RUN unzip /master.zip

EXPOSE 80

CMD ["python3", "/docker-detect-master/detect-app/app.py"]

Lihtne klient detektori jaoks pÔhinev requestsil.

Avaldamine Docker Hubis

Docker registrid tÔukuvad sama kiiresti, kui pilvedetektorid.

Et mitte keeruliseks minna, vÔtame konservatiivse lÀhenemise lÀbi DockerHubi.

  1. Registreerume
  2. Logime sisse:
    docker login
  3. MÔtleme vÀlja sisuka nime:
    docker tag opencv-detect tprlab/opencv-detect-ssd
  4. Laeme pildi serverisse:
    docker push tprlab/opencv-detect-ssd

KĂ€ivitame pilves

Valik, kus konteinerit kĂ€ivitada, on samuti ĂŒsna lai.

KÔik suured tegijad (Google, Microsoft, Amazon) pakuvad esimese aasta jooksul tasuta mikroinstantsi.
Katsusin Microsoft Azure’i ja Google Cloudi, kuid peatusin viimase juures — sest see tĂ”usis kiiremini.

Ei hakanud siia juhendit kirjutama, kuna see osa on vÀga spetsiifiline valitud teenusepakkuja jaoks.

Proovisin erinevaid rauavariante,
Madala taseme (jagatud ja pĂŒhendatud) — 0,4 — 0,5 sekundit.
Tugevamad masinad — 0,25 — 0,3.
Noh, isegi halvemal juhul on vÔit kolme korda, proovi Àra.

Video

KÀivitame lihtsa OpenCV videostreami Raspberryl, tuvastades lÀbi Google Cloud.
Eksperimendi jaoks kasutati videofaili, mis on kunagi filmitud juhuslikul ristmikul.


def handle_frame(frame):
    return detect.detect_draw_img(frame)
       
def generate():
    while True:
        rc, frame = vs.read()
        outFrame = handle_frame(frame)
        if outFrame is None:
            (rc, outFrame) = cv.imencode(".jpg", frame)
        yield(b'--framern' b'Content-Type: image/jpegrnrn' + bytearray(outFrame) + b'rn')

@app.route("/stream")
def video_feed():
    return Response(generate(), mimetype = "multipart/x-mixed-replace; boundary=frame")

Detektoriga ei saa rohkem kui kolm kaadrit sekundis, kÔik toimub vÀga aeglaselt.
Kui GCloudis vÔtta vÔimas masin, vÔib tuvastada 4-5 kaadrit sekundis, kuid silmaga on erinevus praktiliselt mÀrkamatud, ikkagi aeglane.

Video objekti tuvastamise kohta Raspberry Pi-l

Pilv ja transpordikulud siin ei mÀngi rolli, tavalisel riistvaral töötab detektor sellise kiirus.

Neural Computer Stick

Ei suutnud end tagasi hoida ja jooksin NCS-il benchmark'i.

Detektori kiirus oli natuke aeglasem kui 0.1 sekundit, igal juhul 2-3 korda kiiremini kui pilves nÔrkal masinal, s.t 8-9 kaadrit sekundis.

Video objekti tuvastamise kohta Raspberry Pi-l

Tulemustes on erinevus seletatav sellega, et NCS-il kÀivitati Mobile SSD versioon 2018_01_28.

P.S. Lisaks on katsetused nÀidanud, et piisavalt vÔimas lauaarvuti, millel on I7 protsessor, nÀitab veidi paremaid tulemusi ja sellel Ônnestub saavutada 10 kaadrit sekundis.

Klaster

Eksperiment lÀks kaugemale ja paigaldasin detektori viiele sÔlmele Google Kuberneteses.
Isegi konteinerid olid nĂ”rgad ja igaĂŒhel neist ei Ă”nnestunud töödelda rohkem kui 2 kaadrit sekundis.
Kuid kui kĂ€ivitada klaster N sĂ”lmel ja jagada kaadreid N voogu — siis piisava arvu sĂ”lmade (5) korral on vĂ”imalik saavutada soovitud 10 kaadrit sekundis.

def generate():
    while True:
        rc, frame = vs.read()
        if frame is not None:
            future = executor.submit(handle_frame, (frame.copy()))
            Q.append(future)

        keep_polling = len(Q) > 0
        while(keep_polling):            
            top = Q[0]
            if top.done():
                outFrame = top.result()
                Q.popleft()
                if outFrame:
                    yield(b'--framern' b'Content-Type: image/jpegrnrn' + bytearray(outFrame) + b'rn')
                keep_polling = len(Q) > 0
            else:
                keep_polling = len(Q) >= M

Siin on tulemused:

Video objekti tuvastamise kohta Raspberry Pi-l

Veidi mitte nii kiiresti nagu NCS-iga, kuid kiiremini kui ĂŒhes voos.

Kasum ei ole loomulikult lineaarne — tekivad sĂŒnkroniseerimise ja sĂŒgava kopeerimise probleemid opencv piltide puhul.

KokkuvÔte

Üldiselt vĂ”imaldab eksperiment jĂ€reldada, et kui pingutada, on lihtsa pilve toestamine vĂ”imalik.

Kuid vÔimas töölaua arvuti vÔi kohalik server annab paremaid tulemusi, ilma igasuguste trikkideta.

Lingid

Allikas: habr.com

Osta usaldusvÀÀrne veebihosting DDoS kaitsega, VPS VDS serverid đŸ”„ Osta usaldusvÀÀrne veebihosting DDoS kaitsega, VPS VDS serverid | ProHoster