PHP, pobierz nazwę pliku bez rozszerzenia pliku

205

Mam ten kod PHP:

function ShowFileExtension($filepath)
{
    preg_match('/[^?]*/', $filepath, $matches);
    $string = $matches[0];

    $pattern = preg_split('/\./', $string, -1, PREG_SPLIT_OFFSET_CAPTURE);

    if(count($pattern) > 1)
    {
        $filenamepart = $pattern[count($pattern)-1][0];
        preg_match('/[^?]*/', $filenamepart, $matches);
        return strtolower($matches[0]);
    }
}

Jeśli mam plik o nazwie my.zip, funkcja ta zwraca .zip.

Chcę zrobić odwrotnie, chcę, aby funkcja powróciła mybez rozszerzenia.

Plik jest tylko ciągiem w zmiennej.

Mostafa Elkady
źródło

Odpowiedzi:

397

Nie trzeba tego wszystkiego. Sprawdź pathinfo () , daje ci wszystkie składniki twojej ścieżki.

Przykład z instrukcji:

$path_parts = pathinfo('/www/htdocs/index.html');

echo $path_parts['dirname'], "\n";
echo $path_parts['basename'], "\n";
echo $path_parts['extension'], "\n";
echo $path_parts['filename'], "\n"; // filename is only since PHP 5.2.0

Wyjście kodu:

/www/htdocs
index.html
html
index

Alternatywnie możesz uzyskać tylko niektóre części, takie jak:

echo pathinfo('/www/htdocs/index.html', PATHINFO_EXTENSION); // outputs html
Czechnologia
źródło
3
Dlaczego zostało to zanegowane? Odpowiedź jest absolutnie poprawna. pathinfo działa na ciągach, więc nie ma znaczenia, czy plik znajduje się na serwerze, czy nie.
Gordon
13
Szkoda, że ​​źle nazwali „basename”, ponieważ zwraca pełną nazwę pliku z rozszerzeniem, a nie nazwę podstawową.
Oscar
1
@Oscar to najszerzej rozumiane znaczenie tego terminu basename. Bez błędnych nazw.
nawfal
1
Jest to bardzo przydatne, szczególnie gdy nie musisz znać rozszerzenia pliku, aby go rozpakować.
Vahid Amiri,
To niezwykle eleganckie rozwiązanie. Sława. To powinno być oznaczone jako poprawna odpowiedź.
Native Coder
199

Alternatywnie pathinfo()możesz użyć

Przykład z podręcznika PHP

$path = "/home/httpd/html/index.php";
$file = basename($path);         // $file is set to "index.php"
$file = basename($path, ".php"); // $file is set to "index"

Musisz jednak znać rozszerzenie, aby je usunąć wcześniej.

Ponieważ jednak twoje pytanie sugeruje, że potrzebujesz rozszerzenia i nazwy basename, głosowałbym na odpowiedź Pekki jako najbardziej przydatną, ponieważ dostarczy ci ona wszelkich informacji na temat ścieżki i pliku z jednym rodzimym funkcjonować.

Gordon
źródło
1
co jeśli nie wiem o rozszerzeniu pliku ... powiedzmy, że jeśli ścieżka jest dynamiczna, może w niej pojawić się dowolny typ rozszerzenia pliku !! co wtedy?
user889030,
@ user889030, to masz inny scenariusz niż PO i nie korzystaj basename, ale pathinfojak pokazano na stronie.
Gordon
72

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

pathinfo($path, PATHINFO_FILENAME);

Prosty test funkcjonalny: https://ideone.com/POhIDC

yckart
źródło
Zwróci
2
@ user966939 Mhh, nie z rozszerzeniem jest basename;-)
yckart
Cóż, tak czy inaczej, MÓWIŁ o rozwiązanie BEZ rozszerzenia. ;)
user966939
2
@ user966939, Stary, w ogóle nie ma rozszerzenia. Nie PATHINFO_FILENAME, nie PATHINFO_EXTENSION ....
Pacerier
20
Ktokolwiek zdecydował, że filenamenie ma przedłużenia, basenamemusi mieć pewne sadystyczne tendencje ...
Mark
12

Innym podejściem jest użycie wyrażeń regularnych.

$fileName = basename($filePath);
$fileNameNoExtension = preg_replace("/\.[^.]+$/", "", $fileName);

Spowoduje to usunięcie z ostatniego okresu .do końca ciągu.

caiosm1005
źródło
Podoba mi się ta odpowiedź, bardzo prosta i działa, gdy nie znasz rozszerzenia.
powtórka
Znacznie lepiej niż używanie eksplozji, i łapie tylko ostatnią sekcję okresu, jeśli użyłeś kropek w nazwach plików
Kiwizoom
7
Nie , jest o wiele gorzej. Przestań regexować ludzi.
Pacerier
Dzięki, a powyższe komentarze go przybiły. Brak konieczności znajomości rozszerzenia czyni to bardziej przydatnym.
James Taylor
1
@ caiosm1005, Powierzchnia ataku natychmiast wzrasta, ponieważ trudno jest uzasadnić wnętrze silnika wyrażenia regularnego. Na przykład w powyższym kodzie nie byłoby dziwne, gdyby były jakieś dane wejściowe, $fileNamektóre mogłyby spowodować uruchomienie silnika w wykładniczym (lub gorszym) czasie. Zakładając, że zakończyliśmy analizowanie wewnętrznych elementów tego konkretnego silnika regex i teoretycznie udowodniliśmy, że jest on odporny na każdą możliwą możliwą wartość $fileName, kod nadal nie jest arbitralnie przenośny na inną platformę, która ma inną implementację silnika regex.
Pacerier,
12

Jeśli rozszerzenie nie jest znane, skorzystaj z tego rozwiązania

 pathinfo('D:/dir1/dir2/fname', PATHINFO_FILENAME); // return "fname"
 pathinfo('D:/dir1/dir2/fname.php', PATHINFO_FILENAME); // return "fname"
 pathinfo('D:/dir1/dir2/fname.jpg', PATHINFO_FILENAME); // return "fname"

 pathinfo('D:/dir1/dir2/fname.jpg', PATHINFO_DIRNAME) . '/' . pathinfo('D:/dir1/dir2/fname.jpg', PATHINFO_FILENAME); // return "D:/dir1/dir2/fname"

Pathinfo funkcji PHP MAN

anydasa
źródło
Podaj podobny do strony man php dla pathinfo. Pomoże to OP ulepszyć ShowFileExtensionmetodę i zapewni dodatkową lekturę każdemu, kto spróbuje znaleźć tę odpowiedź. Również trochę opisu nie zejdzie na manowce ...
Michael Coxon
1
Odpowiedziałem już na to pytanie w ten sam sposób, ~ 2 lata przed tobą;)
yckart
@yckart prawda, ale daje to wiele przykładów w odpowiedzi. Twoja ma tę zaletę, że łączy się z ideone.com, ale strona może przejść do trybu offline.
Adam Elsodaney
7

@Gordon basename będzie działał dobrze, jeśli znasz rozszerzenie, jeśli nie możesz użyć opcji rozstrzelenia:

$filename = end(explode(".", $file));
ogień
źródło
1
Proszę kierować do mnie komentarze za pomocą funkcji komentowania pod moją odpowiedzią. Najbardziej odpowiednią funkcją do tego jest pathinfo, dlatego podałem tylko basenamejako alternatywę. Nie ma potrzeby wymyślania na nowo za pathinfopomocą wyrażeń regularnych lub explode.
Gordon
4
@fire, Twoja aktualizacja nie ma sensu. end(explode(".", $file));daje rozszerzenie, a nie nazwę pliku.
Pacerier
7

Prawie wszystkie powyższe rozwiązania mają pokazane pobieranie nazwy pliku ze zmiennej $ path

Poniżej fragmentu otrzyma nazwę aktualnie wykonywanego pliku bez rozszerzenia

echo pathinfo(basename($_SERVER['SCRIPT_NAME']), PATHINFO_FILENAME);

Wyjaśnienie

$ _SERVER [„SCRIPT_NAME”] zawiera ścieżkę bieżącego skryptu.

Rohan Khude
źródło
7

Nie ma potrzeby pisać dużo kodu. Nawet można tego dokonać za pomocą jednego wiersza kodu. Zobacz tutaj

Poniżej znajduje się kod jednego wiersza, który zwraca tylko nazwę pliku i usuwa nazwę rozszerzenia:

<?php
 echo pathinfo('logo.png')['filename'];
?>

Wydrukuje się

logo

Źródło: Usuń rozszerzenie i zwróć tylko nazwę pliku w PHP

Faruque Ahamed Mollick
źródło
4

@fire, ponieważ nazwa pliku używa kropek, możesz uzyskać niewłaściwy wynik. Chciałbym użyć metody @Gordon, ale też pobrać rozszerzenie, więc funkcja basename działa ze wszystkimi rozszerzeniami, tak jak to:

$path = "/home/httpd/html/index.php";
$ext = pathinfo($path, PATHINFO_EXTENSION);

$file = basename($path, ".".$ext); // $file is set to "index"
NSINE
źródło
4

w moim przypadku używam poniżej. Nie obchodzi mnie, jakie jest jego rozszerzenie. : D Myślę, że to ci pomoże

$exploded_filepath = explode(".", $filepath_or_URL);
$extension = end($exploded_filepath);
echo basename($filepath_or_URL, ".".$extension ); //will print out the the name without extension.
Hoàng Vũ Tgtt
źródło
Btw .: Masz literówkę$extenion
Thomas Kekeisen
2

Możesz to napisać

$filename = current(explode(".", $file));

Zwrócą bieżący element tablicy, jeśli nie był wcześniej używany.

Jitendra Pawar
źródło
Cześć, proszę sprawdzić przed obniżeniem oceny. Działa, używałem go wiele razy w kodzie. Korzystając z tej funkcji, możesz uzyskać tylko nazwę pliku Jeśli nazwa pliku to „xyz.jpg”. Może nie działać z nazwami plików zawierających całą ścieżkę.
Jitendra Pawar
To również nie działa poprawnie, jeśli nazwa pliku zawiera wiele kropek, np. „Some.interesting.image.jpg”
ganzpopp
2

Krótki

echo pathinfo(__FILE__)['filename']; // since php 5.2
mariovials
źródło
dobry. Ale jeśli wstawię powyższy kod b.phpi wykonam a.phpto require('b.php'). Następnie wyjście będzie jak bzamiasta
Rohan Khude
1

Nazwa pliku bez rozszerzenia, jeśli nie znasz tego rozszerzenia:

$basename = substr($filename, 0, strrpos($filename, "."));

użytkownik2047861
źródło
2
Co powiesz na to, jeśli rozszerzenie jest podobne do .tar.gz?
Arda,
1

Jeśli nie wiesz, jakie masz rozszerzenie, możesz spróbować:

$ext = strtolower(substr('yourFileName.ext', strrpos('yourFileName.ext', '.') + 1));
echo basename('yourFileName.ext','.'.$ext); // output: "youFileName" only

Praca ze wszystkimi możliwościami:

image.jpg // output: "image"
filename.image.png // output: "filename.image"
index.php // output: "index"
Ghanshyam Gohel
źródło
1

Twoja odpowiedź jest poniżej idealnego rozwiązania, aby ukryć rozszerzenie pliku w php.

<?php
    $path = "http://$_SERVER[HTTP_HOST]$_SERVER[REQUEST_URI]";
    echo basename($path, ".php");
?>
shaz3e
źródło
1

Istniejące rozwiązania zawodzą, gdy rozszerzenie składa się z wielu części. Poniższa funkcja działa w przypadku wielu części, pełnej ścieżki lub po prostu nazwy pliku:

function removeExt($path)
{
    $basename = basename($path);
    return strpos($basename, '.') === false ? $path : substr($path, 0, - strlen($basename) + strlen(explode('.', $basename)[0]));
}

echo removeExt('https://example.com/file.php');
// https://example.com/file
echo removeExt('https://example.com/file.tar.gz');
// https://example.com/file
echo removeExt('file.tar.gz');
// file
echo removeExt('file');
// file
Dan Bray
źródło
0

Zwraca tylko nazwę pliku bez rozszerzenia w 1 rzędzie:

$path = "/etc/sudoers.php";    
print array_shift(explode(".", basename($path)));
// will print "sudoers"

$file = "file_name.php";    
print array_shift(explode(".", basename($file)));
// will print "file_name"
Vincenzo Ruffa
źródło