Java使用多線程保存圖片并返回保存路徑

通過圖片的鏈接(如:https://upload-images.jianshu.io/upload_images/11722017-e806b092026a0502.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/628/format/webp
將圖片下載到本地幅垮,并且返回保存的路徑遮咖,然后將路徑保存到數(shù)據(jù)庫中,由于數(shù)據(jù)量較多亭病,可以通過使用多線程的方式縮短處理的時間

線程類

/**
 * 使用多線程處理批量圖片的保存操作
 * @version 1.0.0
 */
public class RunnableSavePicture implements Runnable {

    private static final Logger LOGGER = LoggerFactory.getLogger(RunnableSavePicture.class);

    // 空List陶夜,用于存放已經(jīng)處理好圖片的TrademarkInfoDTO對象
    private List<TrademarkInfoDTO> emptySaveDataList;
    // 傳遞過來的包含圖片鏈接的對象
    private TrademarkInfoDTO trademarkInfoDTO;
    // 保存路徑
    private String filePath;

    public RunnableSavePicture(TrademarkInfoDTO trademarkInfoDTO, List<TrademarkInfoDTO> emptySaveDataList, String filePath) {
        this.trademarkInfoDTO = trademarkInfoDTO;
        this.emptySaveDataList = emptySaveDataList;
        this.filePath = filePath;
    }

    @Override
    public void run() {
        try {
            String oldUrl = trademarkInfoDTO.getTrademarkImgPath();
            if (!StringUtils.isBlank(oldUrl)) {
                byte[] imageByte = null;
                // 用于請求圖片不成功時翰意,再次請求
                int count = 0;
                while (null == imageByte || imageByte.length < 1024) {
                    // 通過鏈接請求圖片返回byte[]用于保存
                    imageByte = HttpUtil.getPicutre(oldUrl);
                    // 3次失敗則放棄
                    if (count > 3) break;
                    count++;
                }
                // 使用UUID生成圖片文件名
                String fileName = UUID.randomUUID().toString().replaceAll("-", "");
                // 將圖片保存到本地
                saveFile(filePath, imageByte, fileName, "jpg");
                // 設(shè)置路徑
                trademarkInfoDTO.setTrademarkImgPath("/icon/" + fileName + ".jpg");
                // 添加到空List中(用于保存到數(shù)據(jù)庫)
                emptySaveDataList.add(trademarkInfoDTO);
            }
        } catch (Exception e) {
            e.printStackTrace();
            LOGGER.debug("==【線程內(nèi)保存圖片操作】==執(zhí)行異常约郁,注冊號:" + trademarkInfoDTO.getTrademarkNum());
            LOGGER.debug("==【線程內(nèi)保存圖片操作】==執(zhí)行異常" + e);
        }
    }

    /*
     * @描述:保存圖片
     * @param:[basePath-存儲路徑, content-圖片byte, fileName-圖片名稱, fileType-圖片類型]
     * @return:void
     */
    private static void saveFile(String basePath, byte[] content, String fileName, String fileType) throws Exception {
        File savePath = new File(basePath);
        if (!savePath.exists()) {
            savePath.mkdir();
        }
        File file = new File(savePath.getAbsolutePath() + "/" + fileName + "." + fileType);
        FileOutputStream fos = new FileOutputStream(file);
        fos.write(content);
        fos.close();
    }

}

使用方法

    public static void main(String[] args) {
        // 從數(shù)據(jù)庫中查詢出圖片鏈接
        List<TrademarkInfoDTO> canSaveDataList = trademarkTemporaryMapper.getCanSaveDataList(adminUid);
        // 當(dāng)前為空List战惊,在線程內(nèi)處理好圖片后流昏,會將傳遞過去的TrademarkInfoDTO對象放進(jìn)該List中
        List<TrademarkInfoDTO> emptySaveDataList = new ArrayList<>();

        long startTime = System.currentTimeMillis();

        String filePath = "E:\\icon\\";
        int availProcessors = Runtime.getRuntime().availableProcessors();
        LOGGER.debug("==【多線程處理圖片】==使用線程數(shù):" + (availProcessors * 2));
        ExecutorService executorService = Executors.newFixedThreadPool(availProcessors * 2);
        for (TrademarkInfoDTO trademarkInfoDTO : canSaveDataList) {
            executorService.execute(new RunnableSavePicture(trademarkInfoDTO, emptySaveDataList, filePath));
        }
        executorService.shutdown();
        executorService.awaitTermination(Long.MAX_VALUE, TimeUnit.DAYS);
        LOGGER.debug("==【多線程處理圖片】==圖片保存執(zhí)行完畢,共保存圖片:" + emptySaveDataList.size() +
                "張吞获,用時:" + (System.currentTimeMillis() - startTime));

        // 執(zhí)行批量插入操作
        int count = trademarkTemporaryMapper.saveAllCrawlTrademark(emptySaveDataList);
        LOGGER.debug("==【保存數(shù)據(jù)操作執(zhí)行完畢】==共保存:" + count);
    }

用到的 HttpUtil 工具類

public class HttpUtil {

    /*
     * @描述:通過圖片鏈接下載圖片并返回byte[]
     * @param:[url]
     * @return:byte[]
     */
    public static byte[] getPicutre(String url) throws Exception {
        byte[] data;
        try {
            Request request = new Request.Builder().url(url).build();
            com.squareup.okhttp.Response response = CLIENT.newCall(request).execute();
            data = response.body().bytes();
        } catch (Exception e) {
            return null;
        }
        return data;
    }

}

用到okhttp况凉,pom.xml需要導(dǎo)入下面兩個jar包

        <!-- https://mvnrepository.com/artifact/com.squareup.okhttp/okhttp -->
        <dependency>
            <groupId>com.squareup.okhttp</groupId>
            <artifactId>okhttp</artifactId>
            <version>2.7.5</version>
        </dependency>

        <!-- https://mvnrepository.com/artifact/com.squareup.okio/okio -->
        <dependency>
            <groupId>com.squareup.okio</groupId>
            <artifactId>okio</artifactId>
            <version>1.13.0</version>
        </dependency>
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市各拷,隨后出現(xiàn)的幾起案子刁绒,更是在濱河造成了極大的恐慌,老刑警劉巖烤黍,帶你破解...
    沈念sama閱讀 211,194評論 6 490
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件知市,死亡現(xiàn)場離奇詭異,居然都是意外死亡速蕊,警方通過查閱死者的電腦和手機(jī)初狰,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,058評論 2 385
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來互例,“玉大人奢入,你說我怎么就攤上這事∠边叮” “怎么了腥光?”我有些...
    開封第一講書人閱讀 156,780評論 0 346
  • 文/不壞的土叔 我叫張陵,是天一觀的道長糊秆。 經(jīng)常有香客問我武福,道長,這世上最難降的妖魔是什么痘番? 我笑而不...
    開封第一講書人閱讀 56,388評論 1 283
  • 正文 為了忘掉前任捉片,我火速辦了婚禮,結(jié)果婚禮上汞舱,老公的妹妹穿的比我還像新娘伍纫。我一直安慰自己,他們只是感情好昂芜,可當(dāng)我...
    茶點故事閱讀 65,430評論 5 384
  • 文/花漫 我一把揭開白布莹规。 她就那樣靜靜地躺著,像睡著了一般泌神。 火紅的嫁衣襯著肌膚如雪良漱。 梳的紋絲不亂的頭發(fā)上舞虱,一...
    開封第一講書人閱讀 49,764評論 1 290
  • 那天,我揣著相機(jī)與錄音母市,去河邊找鬼矾兜。 笑死,一個胖子當(dāng)著我的面吹牛患久,可吹牛的內(nèi)容都是我干的焕刮。 我是一名探鬼主播,決...
    沈念sama閱讀 38,907評論 3 406
  • 文/蒼蘭香墨 我猛地睜開眼墙杯,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了括荡?” 一聲冷哼從身側(cè)響起高镐,我...
    開封第一講書人閱讀 37,679評論 0 266
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎畸冲,沒想到半個月后嫉髓,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 44,122評論 1 303
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡邑闲,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 36,459評論 2 325
  • 正文 我和宋清朗相戀三年算行,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片苫耸。...
    茶點故事閱讀 38,605評論 1 340
  • 序言:一個原本活蹦亂跳的男人離奇死亡州邢,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出褪子,到底是詐尸還是另有隱情量淌,我是刑警寧澤,帶...
    沈念sama閱讀 34,270評論 4 329
  • 正文 年R本政府宣布嫌褪,位于F島的核電站呀枢,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏笼痛。R本人自食惡果不足惜裙秋,卻給世界環(huán)境...
    茶點故事閱讀 39,867評論 3 312
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望缨伊。 院中可真熱鬧摘刑,春花似錦、人聲如沸刻坊。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,734評論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽紧唱。三九已至活尊,卻和暖如春隶校,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背蛹锰。 一陣腳步聲響...
    開封第一講書人閱讀 31,961評論 1 265
  • 我被黑心中介騙來泰國打工深胳, 沒想到剛下飛機(jī)就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人铜犬。 一個月前我還...
    沈念sama閱讀 46,297評論 2 360
  • 正文 我出身青樓舞终,卻偏偏與公主長得像,于是被迫代替她去往敵國和親癣猾。 傳聞我的和親對象是個殘疾皇子敛劝,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 43,472評論 2 348

推薦閱讀更多精彩內(nèi)容