Как получить имя файла по полному пути, используя JavaScript?

310

Есть ли способ, которым я могу получить последнее значение (на основе символа '\') из полного пути?

Пример:

C:\Documents and Settings\img\recycled log.jpg

В этом случае я просто хочу получить recycled log.jpgполный путь в JavaScript.

Джин Юн
источник

Ответы:

698
var filename = fullPath.replace(/^.*[\\\/]/, '')

Это будет обрабатывать как \ OR / в путях

nickf
источник
4
Не работает на MAC OSX, используя chrome, он экранирует символ после \
Pankaj Phartiyal
7
В соответствии с этого сайта, используя replaceэто гораздо медленнее , чем substr, который может быть использован в сочетании с lastIndexOf('/')+1: jsperf.com/replace-vs-substring
Nate
1
@nickf Ник, не уверен, где я ошибаюсь, но код не работает для меня, когда путь к файлу имеет одну косую черту. Fiddle, хотя для `\\` , работает нормально.
Шуб
1
Я просто запустил это на своей консоли, и он отлично работал для "/var/drop/foo/boo/moo.js".replace(/^.*[\\\/]/, '')moo.js
слешей
1
@ZloySmiertniy Есть несколько хороших онлайн-объяснений регулярных выражений. rick.measham.id.au/paste/explain.pl?regex=%2F%5E . *% 5B% 5C% 5C% 5C% 2F% 5D% 2F и regexper.com/#%2F%5E . *% 5B % 5C% 5C% 5C% 2F% 5D% 2F должно помочь. (Ссылки здесь неработающие, но скопируйте и вставьте их во вкладку, и это сработает)
nickf
115

Ради производительности я проверил все ответы, приведенные здесь:

var substringTest = function (str) {
    return str.substring(str.lastIndexOf('/')+1);
}

var replaceTest = function (str) {
    return str.replace(/^.*(\\|\/|\:)/, '');
}

var execTest = function (str) {
    return /([^\\]+)$/.exec(str)[1];
}

var splitTest = function (str) {
    return str.split('\\').pop().split('/').pop();
}

substringTest took   0.09508600000000023ms
replaceTest   took   0.049203000000000004ms
execTest      took   0.04859899999999939ms
splitTest     took   0.02505500000000005ms

И победителем стал ответ в стиле Split и Pop , благодаря bobince !

Danpe
источник
4
В мета-дискуссии, пожалуйста, добавьте соответствующую ссылку на другие ответы. Также было бы полезно лучше объяснить, как вы анализировали среду выполнения.
jpmc26
Не стесняйтесь тестировать и эту версию. Должны поддерживать пути к файлам Mac и Windows. path.split(/.*[\/|\\]/)[1];
tfmontague
2
Тест неверен. substringTest ищет только косую черту, execTest - только обратную косую черту, а два оставшихся обрабатывают обе косые черты. И реальные результаты не имеют значения (больше). Проверьте это: jsperf.com/name-from-path
Горе
@ Горе эта ссылка больше не действительна.
Пакогомес
88

В Node.js вы можете использовать модуль разбора Path ...

var path = require('path');
var file = '/home/user/dir/file.txt';

var filename = path.parse(file).base;
//=> 'file.txt'
RobLoach
источник
14
При использовании Node.js вы можете просто использовать basenameфункцию:path.basename(file)
electrovir
66

С какой платформы идет путь? Пути Windows отличаются от путей POSIX, отличаются от путей Mac OS 9, отличаются от путей ОС RISC, которые отличаются ...

Если это веб-приложение, в котором имя файла может быть с разных платформ, единого решения не существует. Однако разумным ударом является использование как '\' (Windows), так и '/' (Linux / Unix / Mac, а также альтернатива в Windows) в качестве разделителей пути. Вот не-RegExp версия для дополнительного удовольствия:

var leafname= pathname.split('\\').pop().split('/').pop();
bobince
источник
Возможно, вы захотите добавить, что классический MacOS (<= 9) использует разделители двоеточия (:), но я не знаю ни одного браузера, который все еще может использоваться, который не переводил пути MacOS в пути POSIX в виде файла : ///path/to/file.ext
век
4
Вы можете просто использовать pop () вместо reverse () [0]. Он также изменяет исходный массив, но это нормально в вашем случае.
Четан Шастри
Мне интересно, как мы можем создать коллегу, чтобы получить только путь.
Тодд Хорст
Нечто подобное var path = '\\Dir2\\Sub1\\SubSub1'; //path = '/Dir2/Sub1/SubSub1'; path = path.split('\\').length > 1 ? path.split('\\').slice(0, -1).join('\\') : path; path = path.split('/').length > 1 ? path.split('/').slice(0, -1).join('/') : path; console.log(path);
Тодд Хорст
Наименование « имя листа » происходит от имени структуры каталогов / файлов «Дерево», первым элементом дерева является root , последними являются листья => имя файла является последним в пути к дереву => leaf :-)
jave. Веб
29

Ates, ваше решение не защищает от пустой строки в качестве ввода. В этом случае это не с TypeError: /([^(\\|\/|\:)]+)$/.exec(fullPath) has no properties.

bobince, вот версия nickf, которая обрабатывает разделители пути DOS, POSIX и HFS (и пустые строки):

return fullPath.replace(/^.*(\\|\/|\:)/, '');
user129661
источник
4
если мы пишем этот JS-код на PHP, нам нужно добавить по одной дополнительной \ для каждого \
Ленин Радж Раджасекаран
17

Следующая строка кода JavaScript даст вам имя файла.

var z = location.pathname.substring(location.pathname.lastIndexOf('/')+1);
alert(z);
Epperlyg
источник
10

Не более краткий, чем ответ Никфа , но этот непосредственно «извлекает» ответ вместо замены ненужных частей пустой строкой:

var filename = /([^\\]+)$/.exec(fullPath)[1];
Атес Горал
источник
8

Вопрос с вопросом «получить имя файла без расширения» приведен здесь, но решения для этого нет. Вот решение, модифицированное из решения Бобби.

var name_without_ext = (file_name.split('\\').pop().split('/').pop().split('.'))[0];
Рэймонд Син
источник
6

Другой

var filename = fullPath.split(/[\\\/]/).pop();

Здесь split имеет регулярное выражение с классом символов
. Два символа должны быть экранированы с помощью \

Или использовать массив для разделения

var filename = fullPath.split(['/','\\']).pop();

Это был бы способ динамически помещать больше разделителей в массив, если это необходимо.
Если fullPathв вашем коде явно задана строка, она должна быть без обратной косой черты !
подобно"C:\\Documents and Settings\\img\\recycled log.jpg"


источник
3

Я использую:

var lastPart = path.replace(/\\$/,'').split('\\').pop();

Он заменяет последний, \поэтому он также работает с папками.

pomber
источник
2
<script type="text/javascript">
    function test()
    {
        var path = "C:/es/h221.txt";
        var pos =path.lastIndexOf( path.charAt( path.indexOf(":")+1) );
        alert("pos=" + pos );
        var filename = path.substring( pos+1);
        alert( filename );
    }
</script>
<form name="InputForm"
      action="page2.asp"
      method="post">
    <P><input type="button" name="b1" value="test file button"
    onClick="test()">
</form>
Питер Мортенсен
источник
1

Полный ответ:

<html>
    <head>
        <title>Testing File Upload Inputs</title>
        <script type="text/javascript">

        function replaceAll(txt, replace, with_this) {
            return txt.replace(new RegExp(replace, 'g'),with_this);
        }

        function showSrc() {
            document.getElementById("myframe").href = document.getElementById("myfile").value;
            var theexa = document.getElementById("myframe").href.replace("file:///","");
            var path = document.getElementById("myframe").href.replace("file:///","");
            var correctPath = replaceAll(path,"%20"," ");
            alert(correctPath);
        }
        </script>
    </head>
    <body>
        <form method="get" action="#"  >
            <input type="file"
                   id="myfile"
                   onChange="javascript:showSrc();"
                   size="30">
            <br>
            <a href="#" id="myframe"></a>
        </form>
    </body>
</html>
Сандип Кумар
источник
1

Маленькая функция для включения в ваш проект для определения имени файла по полному пути для Windows, а также по абсолютным путям GNU / Linux & UNIX.

/**
 * @param {String} path Absolute path
 * @return {String} File name
 * @todo argument type checking during runtime
 * @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/includes
 * @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/slice
 * @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String/lastIndexOf
 * @example basename('/home/johndoe/github/my-package/webpack.config.js') // "webpack.config.js"
 * @example basename('C:\\Users\\johndoe\\github\\my-package\\webpack.config.js') // "webpack.config.js"
 */
function basename(path) {
  let separator = '/'

  const windowsSeparator = '\\'

  if (path.includes(windowsSeparator)) {
    separator = windowsSeparator
  }

  return path.slice(path.lastIndexOf(separator) + 1)
}
Амин НАИРИ
источник
0
<html>
    <head>
        <title>Testing File Upload Inputs</title>
        <script type="text/javascript">
            <!--
            function showSrc() {
                document.getElementById("myframe").href = document.getElementById("myfile").value;
                var theexa = document.getElementById("myframe").href.replace("file:///","");
                alert(document.getElementById("myframe").href.replace("file:///",""));
            }
            // -->
        </script>
    </head>
    <body>
        <form method="get" action="#"  >
            <input type="file" 
                   id="myfile" 
                   onChange="javascript:showSrc();" 
                   size="30">
            <br>
            <a href="#" id="myframe"></a>
        </form>
    </body>
</html>
Семере Хайлу
источник
1
Хотя этот фрагмент кода может решить вопрос, в том числе объяснение действительно помогает улучшить качество вашего сообщения. Помните, что вы отвечаете на вопрос читателей в будущем, и эти люди могут не знать причин, по которым вы предлагаете код.
Ferrybig
0

Успешно скрипт для вашего вопроса, полный тест

<script src="~/Scripts/jquery-1.10.2.min.js"></script>

<p  title="text" id="FileNameShow" ></p>
<input type="file"
   id="myfile"
   onchange="javascript:showSrc();"
   size="30">


<script type="text/javascript">

function replaceAll(txt, replace, with_this) {
    return txt.replace(new RegExp(replace, 'g'), with_this);
}

function showSrc() {
    document.getElementById("myframe").href = document.getElementById("myfile").value;
    var theexa = document.getElementById("myframe").href.replace("file:///", "");
    var path = document.getElementById("myframe").href.replace("file:///", "");
    var correctPath = replaceAll(path, "%20", " ");
   alert(correctPath);
    var filename = correctPath.replace(/^.*[\\\/]/, '')
    $("#FileNameShow").text(filename)
}

Амин Саадати
источник
0

Это решение намного проще и универсальнее как для «имени файла», так и для «пути».

const str = 'C:\\Documents and Settings\\img\\recycled log.jpg';

// regex to split path to two groups '(.*[\\\/])' for path and '(.*)' for file name
const regexPath = /^(.*[\\\/])(.*)$/;

// execute the match on the string str
const match = regexPath.exec(str);
if (match !== null) {
    // we ignore the match[0] because it's the match for the hole path string
    const filePath = match[1];
    const fileName = match[2];
}
Хишам
источник
Качество ответа можно улучшить, добавив некоторые пояснения к вашему коду. Некоторые люди, ищущие этот ответ, могут быть новичками в кодировании или регулярных выражениях, и небольшой текст, чтобы дать контекст, будет иметь большое значение для понимания.
Jmarkmurphy
надеюсь, что так будет лучше :)
Hicham
-3
function getFileName(path, isExtension){

  var fullFileName, fileNameWithoutExtension;

  // replace \ to /
  while( path.indexOf("\\") !== -1 ){
    path = path.replace("\\", "/");
  }

  fullFileName = path.split("/").pop();
  return (isExtension) ? fullFileName : fullFileName.slice( 0, fullFileName.lastIndexOf(".") );
}
Tomas
источник
-3

var file_name = file_path.substring(file_path.lastIndexOf('/'));

shriniket
источник