PNG'yi Linux'ta JPG'ye dönüştüren toplu iş


163

Linux'larda bir grup PNG'yi toplu olarak dönüştürmenin iyi bir yolunu bilen var mı? (Ubuntu kullanıyorum).

Sadece bir kabuk betiğine girebileceğim bir png2jpg dosyası ideal olacaktır.

Yanıtlar:


237

En iyi bahis, Imagemagick'i kullanmak olacaktır.

Asıl kullanım konusunda uzman değilim, ancak bununla ilgili her şeyi yapabileceğinizi biliyorum!

Bir örnek:

convert image.png image.jpg

ve dönüştürülen görüntüyü oluşturmanın yanı sıra orijinali de koruyacaktır. Toplu gelince. Mogrify aracını kullanmanız gerektiğini düşünüyorum (imagemagick’de aynı komut satırından). Bunun eski görüntülerin üzerine yazdığını unutmayın .

Komut:

mogrify -format jpg *.png  

7
Müthiş, tam olarak peşimdeydim ve tekrar kullanacağım. Bu arada, sadece bunu anlamadığım şekilde açıklığa kavuşturmak demek istediğin bu: dönüştürmek ayrı bir çıktı dosyası oluşturmak için kullanılır, mogrify orijinal görüntüyü değiştirmek için kullanılır.
04

1
Saydam arka plana sahip png görüntüleri düzgün bir şekilde jpg'ye dönüşmez.
vishnu

4
mogrify -format jpg -background black -flatten *.png
PNG'leri

3
Linux kutumdaki @KevinCox mogrify -format jpeg img.png2 dosyama ve file img.*bir png, orjinal el değmemiş ve yeni bir jpeg rapor ettikten sonra . Yani mogrifyyok değil , bu durumda orijinal dosyaların üzerine.
neurino,

4
Gönderen mogrifybelgeler: " Bu araç benzerlik gösterir convert(eğer dosya eki değiştirmedikçe orijinal resim dosyasının üzerine yazılır olduğunu hariç -Format Eğer talep değişikliklerle seçeneği). "
janko-m

82

Birkaç çözümüm daha var.

En basit çözüm, en çok bildirildiği gibi. Döngü için basit bir bash.

for i in *.png ; do convert "$i" "${i%.*}.jpg" ; done

Bazı nedenlerden ötürü bash döngülerinden kaçınmaya meyilliyim, bu yüzden isim yönetimi için bash kullanarak daha unixy xargs yaklaşımı var.

ls -1 *.png | xargs -n 1 bash -c 'convert "$0" "${0%.*}.jpg"'

Kullandığım. Aynı anda birden fazla işi çalıştırmak için GNU Parallel'i kullanır ve size performans artışı sağlar. Varsayılan olarak birçok sisteme kurulur ve neredeyse kesinlikle repo'nuzda bulunur (çevrede olması iyi bir programdır).

ls -1 *.png | parallel convert '{}' '{.}.jpg'

İşlerin sayısı, sahip olduğunuz işlemlerin sayısını değiştirir. Çift çekirdekli sistemimde 3 iş kullanarak daha iyi CPU kullanımı buldum.

ls -1 *.png | parallel -j 3 convert '{}' '{.}.jpg'

Bazı istatistikler istiyorsanız (bir ETA, işler tamamlandı, iş başına ortalama süre ...)

ls -1 *.png | parallel --eta convert '{}' '{.}.jpg'

GNU Parallel kullanıyorsanız alternatif bir sözdizimi de vardır.

parallel convert '{}' '{.}.jpg' ::: *.png

Ve diğer bazı sürümler için benzer bir sözdizimi (debian dahil).

parallel convert '{}' '{.}.jpg' -- *.png

2
İçin doğru bash string genişlemesi için +1, paralelden bahsetmek için size başka bir artı verebilirsem, olurdum. Ancak bir yazım hatası var - donebunun için bir döngü gerekiyor. Ayrıca, paralel şeyler için, bunu lsve parallel -j 3 --eta convert '{}' '{.}.jpg' ::: *.png
pipoyu

Sabit yazım hatası. Bu bilmediğim güzel bir sözdizimi. Hangisini daha çok sevdiğimi bilmiyorum muhtemelen aynı sebepten dolayı döngüde bash kullanmamayı tercih ediyorum. Çözümü yaptım çünkü muhtemelen daha "uygun" bir yol ama muhtemelen lskendime göre bir yöntem kullanacağım çünkü bana daha mantıklı geliyor.
Kevin Cox,

1
... sözdiziminin sadece GNU paralelinde çalıştığı belirtilmelidir. Bazı Linux dağıtımlarında paketlenmiş olan paralel (Debian ve Ubuntu gibi) aslında biraz farklı bir sözdizimine sahip farklı bir versiyondur ( --yerine kullanmak :::) - ve o zaman bile, GNU paralelinin bazı özelliklerinden sinir bozucu bir şekilde yoksundur.
kötülük

(GNU paralel paket olmadığını dağıtımlar üzerinde bu talimatları kullanarak, oldukça kolay bir kaynaktan yükleyebilirsiniz gerçi burada )
evilsoup

Sanırım onu ​​daha sonra değiştirmeliyim ki mümkün olduğu kadar çok sürümle çalışsın.
Kevin Cox

26

convertBirçok Linux dağıtımı üzerinde bulunan komut ImageMagick paketinin bir parçası olarak yüklenir. İşte convertbir dizindeki tüm PNG dosyalarında çalışacak bash kodu ve bu çift uzantı probleminden kaçının:

for img in *.png; do
    filename=${img%.*}
    convert "$filename.png" "$filename.jpg"
done

8
Convert Man sayfasına göre: "Convert programı, ImageMagick (1) araçlar grubunun bir üyesidir."
nedned

1
Haklısın. Nedense farklı bir kütüphanenin parçası olduğunu düşündüm. Her iki durumda da yukarıda gönderdiğim kod, bir dizindeki toplu dönüştürmeyi otomatikleştirmek için doğru yoldur.
Marcin

2
Bu komutu geliştirmek için bash genişletmesini kullanabilirsiniz:for f in *.png; do convert "$f" "${f/%png/jpg}"; done
evilsoup 2

Sadece büyük / küçük harfe duyarlı olduğunu hatırla. kameram bunu * .JPG olarak adlandırdı ve ilk etapta bunu anlamadı.
tsenapathy

10

tl; Dr.

Sadece en basit komutları isteyenler için:

Orijinal dosyaları dönüştürün ve saklayın :

mogrify -format jpg *.png

Orijinal dosyaları dönüştürün ve kaldırın :

mogrify -format jpg *.png && rm *.png

Toplu dönüştürme açıklaması

Partiye geç kaldım, ama sadece cli ile çok rahat olmayan biri için tüm kafa karışıklığını gidermek için, işte size aptalca bir referans ve açıklama.

Örnek Dizin

bar.png
foo.png
foobar.jpg

Basit dönüştürme

Tüm orijinal png dosyalarını tutar ve jpg dosyaları oluşturur.

mogrify -format jpg *.png

Sonuç

bar.png
bar.jpg
foo.png
foo.jpg
foobar.jpg

açıklama

  • mogrify , görüntü işleme için ImageMagick araçlar grubunun bir parçasıdır .
    • mogrify , görüntüleri yerinde tutar , yani -formatseçenek hariç, orijinal dosyanın üzerine yazılır . (Gönderen sitede : This tool is similar to convert except that the original image file is overwritten (unless you change the file suffix with the -format option))
  • - formatSeçenek biçimi değiştirmeden olacağını belirtir ve bir sonraki argüman (bu durumda, jpg) tipi olması gerekmektedir.
  • Son olarak, *.pnggirdi dosyalarıdır (.png ile biten tüm dosyalar).

Dönüştür ve Kaldır

Tüm png dosyalarını jpg'ye dönüştürür, orijinali kaldırır.

mogrify -format jpg *.png && rm *.png

Sonuç

bar.jpg
foo.jpg
foobar.jpg

açıklama

  • İlk bölüm yukarıdakiyle tamamen aynı, yeni jpg dosyaları oluşturacak.
  • &&Bir boolean operatörüdür. Kısacası:
    • Bir program sonlandırıldığında, çıkış durumu verir. Bir durum, 0hata yok demektir.
    • Yana &&gerçekleştirdiği kısa devre değerlendirmesinde ise, sağ kısmı sadece yapılacak hiç hata yoktur . Bu, kullanışlıdır, çünkü dönüştürmekte bir hata varsa, tüm orijinal dosyaları silmek istemeyebilirsiniz.
  • rmKomut dosyaları siler.

Süslü sayfalar

Şimdi burada insanlar için bazı güzellikler var olan cli ile rahat.

Dosyaları dönüştürürken bir miktar çıktı almak istiyorsanız:

for i in *.png; do mogrify -format jpg "$i" && rm "$i"; echo "$i converted to ${i%.*}.jpg"; done

Tüm alt dizinlerdeki tüm png dosyalarını dönüştürün ve her birine çıktı verin:

find . -iname '*.png' | while read i; do mogrify -format jpg "$i" && rm "$i"; echo "Converted $i to ${i%.*}.jpg"; done

Tüm alt dizinlerdeki tüm png dosyalarını dönüştürün, elde edilen tüm jpgs'leri alldizine yerleştirin, numaralandırın, orijinal png dosyalarını kaldırın ve gerçekleştiği gibi her dosya için çıktıyı görüntüleyin:

n=0; find . -iname '*.png' | while read i; do mogrify -format jpg "$i" && rm "$i"; fn="all/$((n++)).jpg"; mv "${i%.*}.jpg" "$fn"; echo "Moved $i to $fn"; done

Muhtemelen en iyi cevap, while readparçadan kurtulmak kaydıyla (değiştirmek ya da hepsini birlikte kaldırmak) ...
don_crissti

@ don_crissti, okurken yanlış olan ne?
Steven Jeffries

Hata eğilimli (aklı başında dosya adlarıyla işlediğinizden% 100 emin değilseniz) ve yavaş (çok, çok, çok yavaş gibi).
don_crissti

Varsayılan JPG kalitesi nedir ve dosya zaman damgaları nasıl korunabilir?
Dan Dascalescu

@DanDascalescu Yukarıdaki yöntemler (sonuncusu hariç) dosya adlarını korur, ancak uzantılarını değiştirir, bu nedenle zaman damgalı dosyaların iyi olması gerekir (her zaman önce bir kopya yapın ve önce sınayın). ImageMagick’e göre, "Varsayılan olarak, eğer tespit edilebiliyorsa, giriş resminizin tahmini kalitesini kullanmak mümkündür, aksi takdirde 92" ( imagemagick.org/script/command-line-options.php#quality ) Kalite, -kalite ile belirtilebilir <sayı> burada <sayı> 1 - 100'dür.
Steven Jeffries

8

Gerçek " png2jpgAradığınız" komutu olarak adlandırılan iki komutları içine gerçeklik bölünmüş olduğunu pngtopnmve cjpegve parçası oldukları netpbmve libjpeg-progssırasıyla paketler.

png2pnm foo.png | cjpeg > foo.jpeg

6
find . -name "*.png" -print0 | xargs -0 mogrify -format jpg -quality 50

1
*.jpgÖzgün / özyinelemeli bir dizin için sonuçta ortaya çıkan dosyaları orijinal dosyaların yanında bırakan tek satırlı bir çözüm için teşekkürler *.png, dosya boyutunu / kalitesini nasıl azaltacağını gösterir ve dizin veya dosya adındaki tuhaf karakterler nedeniyle bozulmaz.
Joel Purra

5

hızlı çözümüm for i in $(ls | grep .png); do convert $i $(echo $i.jpg | sed s/.png//g); done


2
Bu, şimdiye kadar gördüğüm en çirkin, en karmaşık komut satırlarından biri
olmalı

1
Dürüst olmak gerekirse @ evilsoup, bu kabuk komut dosyaları için zarif. Katlanmış olduğunu iddia etmek adil değil.
Max Howell

8
@ MaxHowell adam. Hayır İşte bu zarif bir versiyonu olacaktır: for f in ./*.png; do convert "$f" "${f%.*}.jpg"; done. Bu tamamen gereksiz önler ls, grepve sedaramaları (ve echofakat yerleşik bir bash olduğunu ve bu yüzden / hayır çok az performans etkisi olacak IIRC) ve iki boru ve iki altkabuklarda kurtulur, ve daha az yazar içerir. Tüm sürümleri lsayrıştırmak güvenli olmadığından, biraz daha taşınabilir .
kötülük

@ evilsoup Düzeltilmiş duruyorum! Aferin.
Max Howell

4

Yıllar geç kaldı, özellikle bu amaçla yazdığım png2jpeg bir yardımcı programı var .

Kodun @Marcin tarafından uyarlanması:

#!/bin/sh

for img in *.png
do
    filename=${img%.*}
    png2jpeg -q 95 -o "$filename.jpg" "$filename.png"
done

3

Toplu işlem için:

for img in *.png; do
  convert "$img" "$img.jpg"
done

Yine de image1.png.jpg gibi bir dosya adı bulursunuz.

Bu bash olarak çalışacak ve belki de burne. Diğer mermileri bilmiyorum ama tek fark döngü sözdizimi olabilir.


1

Dosyalar birden fazla dizine yayıldığında dönüştürmek için kullandığım şey budur. Orijinalim TGA'dan PNG'ye

find . -name "*.tga" -type f | sed 's/\.tga$//' | xargs -I% convert %.tga %.png

Konsept, findihtiyacınız olan dosyaları açar, uzantıyı çıkartır ve sonra tekrar eklersiniz xargs. Böylece PNG’nin JPG’si için uzantıları değiştirirsiniz ve alfa kanallarıyla başa çıkmak için ek bir şey yaparsınız (arkaplanı beyaza ayarlar) (bu örnekte beyaz olarak değiştirebilirsiniz)

find . -name "*.png" -type f | sed 's/\.png$//' | xargs -I% convert %.png -background white -flatten  %.jpg
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.