Wie bekomme ich eine Dateierweiterung in PHP?


723

Diese Frage können Sie überall im Internet mit verschiedenen Antworten lesen:

$ext = end(explode('.', $filename));
$ext = substr(strrchr($filename, '.'), 1);
$ext = substr($filename, strrpos($filename, '.') + 1);
$ext = preg_replace('/^.*\.([^.]+)$/D', '$1', $filename);

$exts = split("[/\\.]", $filename);
$n    = count($exts)-1;
$ext  = $exts[$n];

usw.

Es gibt jedoch immer "den besten Weg" und es sollte sich um einen Stapelüberlauf handeln.



5
Ein weiterer Weg, um ext zu bekommen, iststrrchr($filename, '.');
Verybadbug

Antworten:


1776

Leute aus anderen Skriptsprachen denken immer, dass ihre besser ist, weil sie eine eingebaute Funktion haben, um das zu tun, und nicht PHP (ich schaue mir gerade Pythonistas an :-)).

Tatsächlich existiert es, aber nur wenige Menschen wissen es. Treffen pathinfo():

$ext = pathinfo($filename, PATHINFO_EXTENSION);

Dies ist schnell und eingebaut. pathinfo()kann Ihnen andere Informationen geben, wie z. B. den kanonischen Pfad, abhängig von der Konstante, die Sie an ihn übergeben.

Denken Sie daran, dass Sie zuerst das Gebietsschema festlegen müssen, wenn Sie mit Nicht-ASCII-Zeichen umgehen möchten. Z.B:

setlocale(LC_ALL,'en_US.UTF-8');

Beachten Sie auch, dass dies nicht den Dateiinhalt oder den MIME-Typ berücksichtigt, sondern nur die Erweiterung. Aber es ist das, wonach du gefragt hast.

Beachten Sie schließlich, dass dies nur für einen Dateipfad funktioniert, nicht für einen URL-Ressourcenpfad, der mit PARSE_URL abgedeckt wird.

Genießen


62
Ich wünschte, ich könnte dies zweimal abstimmen. Ich kann Ihnen nicht sagen, wie viel Code ich mit pathinfo ersetzen konnte
Mark Biek

8
Ich auch. Deshalb habe ich es hier platziert!
E-Satis

7
Wie sich herausstellt, gibt es einen besten Weg.
Ben

19
@khizaransari Du solltest nach einem anderen Hosting-Anbieter suchen, der, den du hast, ist dumm. Wirklich, ich meine es ernst. Es gibt keinerlei Grund , diese Funktion zu deaktivieren. Sag ihnen das. Um dieses Problem zu umgehen: Stellen function get_ext($fname){ return substr($fname, strrpos($fname, ".") + 1); }Sie sicher, dass die Datei eine Erweiterung hat. Sie kann alles tun, wenn Sie einen Pfad als Argument übergeben!
Luc

12
Meine Vorstellung von PHP im Vergleich zu Python hat sich jetzt, da ich über diese Funktion Bescheid weiß, komplett geändert: O
Tommaso Barbugli

166

pathinfo()

$path_info = pathinfo('/foo/bar/baz.bill');

echo $path_info['extension']; // "bill"

14
Seit PHP 5.5 ->echo pathinfo('/foo/bar/baz.bill')['extension'];
Salman A

1
Dies funktioniert sogar auf dieser Ebene (Twitter json): $ ext = pathinfo ($ result-> extended_entities-> media [0] -> video_info-> Varianten [1] -> url, PATHINFO_EXTENSION);
KJS

100

Beispiel-URL: http://example.com/myfolder/sympony.mp3?a=1&b=2#XYZ

A) Verwenden Sie keine empfohlenen unsicherenPATHINFO :

pathinfo($url)['dirname']   🡺 'http://example.com/myfolder'
pathinfo($url)['basename']  🡺 'sympony.mp3?a=1&b=2#XYZ'         // <------- BAD !!
pathinfo($url)['extension'] 🡺 'mp3?a=1&b=2#XYZ'                 // <------- BAD !!
pathinfo($url)['filename']  🡺 'sympony'

B) Verwenden Sie PARSE_URL :

parse_url($url)['scheme']   🡺 'http'
parse_url($url)['host']     🡺 'example.com'
parse_url($url)['path']     🡺 '/myfolder/sympony.mp3'
parse_url($url)['query']    🡺 'aa=1&bb=2'
parse_url($url)['fragment'] 🡺 'XYZ'

BONUS: Alle nativen PHP-Beispiele anzeigen


3
Diese Antwort deckt alles ab, z. Eine Datei wie foo_folder/foo-file.jpg?1345838509wird kläglich mit just pathinfo, thanx

1
Nicht ganz zum Thema, aber es hat mein Problem sicher gelöst!
Howie

7
Vergiss nichts! parse_urlist für URL und pathinfoist für Dateipfad.
Nabi KAZ

1
Was meinst du mit "Pfadinformationen vergessen"? Sie verwenden es in der Lösung!
Herbst Leonard

1
@AutumnLeonard Er tut es nicht, er hat nur die Unterschiede zwischen pathinfo und parse_url gezeigt.

59

Es gibt auch SplFileInfo:

$file = new SplFileInfo($path);
$ext  = $file->getExtension();

Oft können Sie besseren Code schreiben, wenn Sie ein solches Objekt anstelle einer Zeichenfolge weitergeben. Ihr Code spricht dann mehr. Seit PHP 5.4 ist dies ein Einzeiler:

$ext  = (new SplFileInfo($path))->getExtension();

Fantastisch, seine Objekte ganz unten :)
Christopher Chase

2
Bitte beachten Sie, dass ->getExtension()SplFileInfo seit PHP 5.3.6 verfügbar ist.
Matthias

1
@matthias: Bitte beachten Sie, dass SPL in PHP-Versionen vor PHP 5.3.0 deaktiviert werden kann. Wenn Sie immer noch nicht PHP 5.3, sondern 5.2 oder niedriger ausführen, passte diese Antwort höchstwahrscheinlich nicht zu stabilem Code. Andernfalls können Sie Ihren Code stabilisieren, indem Sie eine bestimmte PHP-Version benötigen, und ansonsten aussteigen.
hakre

@hakre Während Sie zu Recht sagen, dass "in Versionen vor 5.3.0 deaktiviert werden kann", wird die SPL-Erweiterung ab PHP 5.0.0 standardmäßig kompiliert. Daher ist dieser Kommentar in der Tat sinnvoll für Personen, die gezwungen sind, PHP 5.2 oder niedriger zu verwenden, und nicht mit bestimmten SPL-Klassen zurücktreten möchten.
Matthias

Ja, nur tote Version Fluff :)
hakre

23

Die Antwort von E-satis ist der richtige Weg, um die Dateierweiterung zu bestimmen.

Anstatt sich auf eine Dateierweiterung zu verlassen, können Sie alternativ die Dateieinfo verwenden , um den MIME-Typ der Dateien zu bestimmen.

Hier ist ein vereinfachtes Beispiel für die Verarbeitung eines von einem Benutzer hochgeladenen Bildes:

// Code assumes necessary extensions are installed and a successful file upload has already occurred

// Create a FileInfo object
$finfo = new FileInfo(null, '/path/to/magic/file');

// Determine the MIME type of the uploaded file
switch ($finfo->file($_FILES['image']['tmp_name'], FILEINFO_MIME)) {        
    case 'image/jpg':
        $im = imagecreatefromjpeg($_FILES['image']['tmp_name']);
    break;

    case 'image/png':
        $im = imagecreatefrompng($_FILES['image']['tmp_name']);
    break;

    case 'image/gif':
        $im = imagecreatefromgif($_FILES['image']['tmp_name']);
    break;
}

1
Dies ist die EINZIGE richtige Antwort. Ich verstehe nicht, warum Leute andere gewählt haben. Ja, dieser Ansatz erfordert vom Entwickler mehr Aufwand, steigert jedoch die Leistung (obwohl wenig, aber er tut es). Bitte beziehen Sie sich darauf .
Bhavik Shah

2
@ Bhavik: In einigen Fällen benötigen wir möglicherweise nur die Dateierweiterung, sie über die MIME-Typprüfung. Die eigentliche Frage betrifft jedoch die Dateierweiterung und nicht den Dateityp. Dies ist also NICHT die beste Antwort auf diese Frage. (noch eine Antwort)
Sasi Varna Kumar

Dieser Schalter benötigt eine zusätzliche Klammer
rsb2097

16

Solange es keinen Pfad enthält, können Sie auch Folgendes verwenden:

array_pop(explode('.', $fname))

Wo $fnameist ein Name der Datei, zum Beispiel : my_picture.jpg. Und das Ergebnis wäre:jpg


@ Warum haben diese 3 Downvotes? es gibt das richtige Ergebnis. Bitte erklären Sie
Railsbox

Es ist nicht falsch, es ist einfach nicht der beste Weg, es zu tun. Für ein bisschen Gleichgewicht gestimmt.

Dies ist der beste Weg, wenn Sie die echte Erweiterung benötigen und der Dateiname möglicherweise mehrere .s enthält, wie in meinem Fall vom Benutzer hochgeladene Fotos.
Rauli Rajande

2
Dies schlägt fehl, wenn der Dateiname keine Erweiterung hat. Versuchen Sie, "myfile" zu übergeben, und es wird "myfile" zurückgegeben. Der korrekte Rückgabewert ist in diesem Anwendungsfall eine leere Zeichenfolge als Erweiterung.
pmont

Dies ist insofern falsch, als array_pop () einen Hinweis auslöst, weil ein Zeiger als Parameter verwendet wird.
Jurchiks

12

1) Wenn Sie (PHP 5> = 5.3.6) verwenden , können Sie SplFileInfo :: getExtension verwenden - Ruft die Dateierweiterung ab

Beispielcode

<?php

$info = new SplFileInfo('test.png');
var_dump($info->getExtension());

$info = new SplFileInfo('test.tar.gz');
var_dump($info->getExtension());

?>

Dies wird ausgegeben

string(3) "png"
string(2) "gz"

2) Eine andere Möglichkeit, die Erweiterung zu erhalten, wenn Sie (PHP 4> = 4.0.3, PHP 5) verwenden, ist pathinfo

Beispielcode

<?php

$ext = pathinfo('test.png', PATHINFO_EXTENSION);
var_dump($ext);

$ext = pathinfo('test.tar.gz', PATHINFO_EXTENSION);
var_dump($ext);

?>

Dies wird ausgegeben

string(3) "png"
string(2) "gz"

// BEARBEITEN: Eine Klammer wurde entfernt


12

Manchmal ist es nützlich, nicht zu verwenden pathinfo($path, PATHINFO_EXTENSION). Zum Beispiel:

$path = '/path/to/file.tar.gz';

echo ltrim(strstr($path, '.'), '.'); // tar.gz
echo pathinfo($path, PATHINFO_EXTENSION); // gz

Beachten Sie auch, dass pathinfoeinige Nicht-ASCII-Zeichen nicht verarbeitet werden können (normalerweise werden sie nur aus der Ausgabe unterdrückt). In Erweiterungen ist das normalerweise kein Problem, aber es tut nicht weh, sich dieser Einschränkung bewusst zu sein.


6
@ e-satis: Laut Wikipedia handelt es sich um zwei Erweiterungen: Die UNIX-ähnlichen Dateisysteme verwenden ein anderes Modell ohne die getrennten Erweiterungsmetadaten. Das Punktzeichen ist nur ein weiteres Zeichen im Hauptdateinamen, und Dateinamen können mehrere Erweiterungen haben, die normalerweise verschachtelte Transformationen darstellen, z. B. files.tar.gz .
Alix Axel

1
Und wenn wir einen Punkt im Produktnamen haben? Beispiel:test.19-02-2014.jpeg
Mario Radomanana

Dies schlägt ltrim(strrchr($PATH, '.'),'.')fehl, wenn /root/my.folder/my.css wie pathinfo funktioniert, ohne jedoch alles zu tokenisieren.
Ray Foss

8

Der einfachste Weg, um eine Dateierweiterung in PHP zu erhalten, ist die Verwendung der in PHP integrierten Funktion pathinfo .

$file_ext = pathinfo('your_file_name_here', PATHINFO_EXTENSION);
echo ($file_ext); // The output should be the extension of the file e.g., png, gif, or html

8

Sie können auch dies versuchen (es funktioniert unter PHP 5. * und 7):

$info = new SplFileInfo('test.zip');
echo $info->getExtension(); // ----- Output -----> zip

Tipp: Es wird eine leere Zeichenfolge zurückgegeben, wenn die Datei keine Erweiterung hat


7

Entschuldigung ... "Kurze Frage; aber NICHT kurze Antwort"

Beispiel 1 für PATH

$path = "/home/ali/public_html/wp-content/themes/chicken/css/base.min.css";
$name = pathinfo($path, PATHINFO_FILENAME);
$ext  = pathinfo($path, PATHINFO_EXTENSION);
printf('<hr> Name: %s <br> Extension: %s', $name, $ext);

Beispiel 2 für URL

$url = "//www.example.com/dir/file.bak.php?Something+is+wrong=hello";
$url = parse_url($url);
$name = pathinfo($url['path'], PATHINFO_FILENAME);
$ext  = pathinfo($url['path'], PATHINFO_EXTENSION);
printf('<hr> Name: %s <br> Extension: %s', $name, $ext);

Ausgabe von Beispiel 1:

Name: base.min
Extension: css

Ausgabe von Beispiel 2:

Name: file.bak
Extension: php

Verweise

  1. https://www.php.net/manual/en/function.pathinfo.php

  2. https://www.php.net/manual/en/function.realpath.php

  3. https://www.php.net/manual/en/function.parse-url.php


6

Eine schnelle Lösung wäre so etwas.

// Exploding the file based on the . operator
$file_ext = explode('.', $filename);

// Count taken (if more than one . exist; files like abc.fff.2013.pdf
$file_ext_count = count($file_ext);

// Minus 1 to make the offset correct
$cnt = $file_ext_count - 1;

// The variable will have a value pdf as per the sample file name mentioned above.
$file_extension = $file_ext[$cnt];

Warum nicht einfach die in PHP integrierte Funktion für den Zweck php.net/manual/en/function.pathinfo.php verwenden, anstatt langen Code zu verwenden
Shahbaz

1
Neben Shahbaz 'Argument können Sie auch $file_ext = end(explode('.', $filename));alles in dieser Antwort in einer einzigen Zeile anstelle von vier tun.
tvanc

@Amelia Was ist, wenn du hast .tar.gz. Es wird nicht funktionieren. Wenn Sie also voll mit Erweiterungen sein müssen, verwenden Sie diese ltrim(strstr($filename, '.'), '.');, um stattdessen voller Korrektur zu werden gz.
Marin Sagovac

6

Hier ist ein Beispiel. Angenommen, $ filename ist "example.txt".

$ext = substr($filename, strrpos($filename, '.', -1), strlen($filename));

$ Ext wird also ".txt" sein.


6

pathinfo ist ein Array. Wir können Verzeichnisnamen, Dateinamen, Erweiterung usw.: Überprüfen .

$path_parts = pathinfo('test.png');

echo $path_parts['extension'], "\n";
echo $path_parts['dirname'], "\n";
echo $path_parts['basename'], "\n";
echo $path_parts['filename'], "\n";

5
substr($path, strrpos($path, '.') + 1);

1
Dies wird mit /root/my.folder/my.css
Ray Foss

1
Dies muss korrekt funktionieren: substr ($ path, strrpos ($ path, '.') + 1); Hinweis: Diese Methode ist schneller als alle anderen oben genannten Lösungen. Probieren Sie einen Benchmark mit unserem eigenen Skript aus.
Abbas

4

Sie können auch Folgendes versuchen:

 pathinfo(basename($_FILES["fileToUpload"]["name"]), PATHINFO_EXTENSION)

4
ltrim(strstr($file_url, '.'), '.')

Dies ist der beste Weg, wenn Sie Dateinamen wie name.name.name.ext haben (hässlich, aber es passiert manchmal



3

Ich habe festgestellt, dass die pathinfo()und SplFileInfo-Lösungen für Standarddateien im lokalen Dateisystem gut funktionieren, aber Sie können auf Schwierigkeiten stoßen, wenn Sie mit Remote-Dateien arbeiten, da URLs für gültige Bilder möglicherweise eine #(Fragment-ID) und / oder ?(Abfrageparameter) haben. am Ende der URL, die beide Lösungen (falsch) als Teil der Dateierweiterung behandeln.

Ich fand, dass dies ein zuverlässiger Weg war pathinfo() eine URL nach dem ersten Parsen zu verwenden, um die unnötige Unordnung nach der Dateierweiterung zu beseitigen:

$url_components = parse_url($url); // First parse the URL
$url_path = $url_components['path']; // Then get the path component
$ext = pathinfo($url_path, PATHINFO_EXTENSION); // Then use pathinfo()

3

Verwenden substr($path, strrpos($path,'.')+1); . Es ist die schnellste Methode aller Vergleiche.

@ Kurt Zhong hat bereits geantwortet.

Überprüfen wir das Vergleichsergebnis hier: https://eval.in/661574


2

Sie können alle Dateierweiterungen in einem bestimmten Ordner abrufen und Vorgänge mit einer bestimmten Dateierweiterung ausführen:

<?php
    $files = glob("abc/*.*"); // abc is the folder all files inside folder
    //print_r($files);
    //echo count($files);
    for($i=0; $i<count($files); $i++):
         $extension = pathinfo($files[$i], PATHINFO_EXTENSION);
         $ext[] = $extension;
         // Do operation for particular extension type
         if($extension=='html'){
             // Do operation
         }
    endfor;
    print_r($ext);
?>

2

Mach es schneller.

Low-Level-Anrufe müssen sehr schnell sein, daher dachte ich, dass es einige Nachforschungen wert ist. Ich habe einige Methoden ausprobiert (mit verschiedenen Stringlängen, Erweiterungslängen, jeweils mehreren Läufen). Hier sind einige vernünftige:

function method1($s) {return preg_replace("/.*\./","",$s);} // edge case problem
function method2($s) {preg_match("/\.([^\.]+)$/",$s,$a);return $a[1];}
function method3($s) {$n = strrpos($s,"."); if($n===false) return "";return substr($s,$n+1);}
function method4($s) {$a = explode(".",$s);$n = count($a); if($n==1) return "";return $a[$n-1];}
function method5($s) {return pathinfo($s, PATHINFO_EXTENSION);}

Die Ergebnisse waren nicht sehr überraschend. Schlecht pathinfoist (bei weitem!) method3()Am langsamsten (es sieht so aus, als würde er versuchen, das Ganze zu analysieren und dann alle unnötigen Teile fallen zu lassen) - und (strrpos) ist bei weitem am schnellsten:

Original filename was: something.that.contains.dots.txt
Running 50 passes with 10000 iterations each
Minimum of measured times per pass:

    Method 1:   312.6 mike  (response: txt) // preg_replace
    Method 2:   472.9 mike  (response: txt) // preg_match
    Method 3:   167.8 mike  (response: txt) // strrpos
    Method 4:   340.3 mike  (response: txt) // explode
    Method 5:  2311.1 mike  (response: txt) // pathinfo  <--------- poor fella

HINWEIS: Die erste Methode hat einen Nebeneffekt: Sie gibt den gesamten Namen zurück, wenn keine Erweiterung vorhanden ist. Sicherlich würde es keinen Sinn machen, es mit einem zusätzlichen Strpos zu messen, um dieses Verhalten zu vermeiden.

Fazit

Das sieht aus wie der Weg der Samurai:

function fileExtension($s) {
    $n = strrpos($s,".");
    return ($n===false) ? "" : substr($s,$n+1);
}

1

Wenn Sie nach Geschwindigkeit suchen (z. B. in einem Router), möchten Sie wahrscheinlich nicht alles tokenisieren. Viele andere Antworten werden mit scheitern/root/my.folder/my.css

ltrim(strrchr($PATH, '.'),'.');

1

Obwohl der "beste Weg" umstritten ist, glaube ich, dass dies aus mehreren Gründen der beste Weg ist:

function getExt($path)
{
    $basename = basename($path);
    return substr($basename, strlen(explode('.', $basename)[0]) + 1);
}
  1. Es funktioniert mit mehreren Teilen zu einer Erweiterung, z tar.gz
  2. Kurzer und effizienter Code
  3. Es funktioniert sowohl mit einem Dateinamen als auch mit einem vollständigen Pfad

1

IMO, dies ist der beste Weg, wenn Sie Dateinamen wie name.name.name.ext haben (hässlich, aber es passiert manchmal):

$ext     = explode('.', $filename); // Explode the string
$ext_len = count($ext) - 1; // Count the array -1 (because count() starts from 1)
$my_ext  = $ext[$ext_len]; // Get the last entry of the array

echo $my_ext;

1

$ext = preg_replace('/^.*\.([^.]+)$/D', '$1', $fileName);

preg_replace Ansatz verwenden wir das Suchen und Ersetzen von regulären Ausdrücken. In der Funktion preg_replace ist der erste Parameter ein Muster für die Suche, der zweite Parameter $ 1 ist eine Referenz auf alles, was mit dem ersten (. *) Übereinstimmt, und der dritte Parameter ist der Dateiname.

Auf andere Weise können wir auch strrpos verwenden, um die Position des letzten Auftretens eines '.' in einem Dateinamen und erhöhen Sie diese Position um 1, so dass die Zeichenfolge von (.) explodiert.

$ext = substr($fileName, strrpos($fileName, '.') + 1);


0

Eigentlich habe ich danach gesucht.

<?php

$url = 'http://example.com/myfolder/sympony.mp3?a=1&b=2#XYZ';
$tmp = @parse_url($url)['path'];
$ext = pathinfo($tmp, PATHINFO_EXTENSION);

var_dump($ext);

-1

Verwenden

str_replace('.', '', strrchr($file_name, '.'))

für einen schnellen Abruf von Erweiterungen (wenn Sie sicher sind, dass Ihr Dateiname einen hat).

Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.