Функция Win32 для определения, является ли файл потомком каталога - PullRequest
0 голосов
/ 28 марта 2011

В C ++, Windows у меня есть 2 пути к файлам:

  • Path1 : каталог
  • Path2 : файл или каталог

Как я могу определить, является ли Path2 потомком Path1?Для этого есть функция Shell?Я искал Shell API и не смог найти ничего.

Примечание: я не хочу сравнивать строку самостоятельно, если только не существует безопасного способа сделать путь сопоставимым (обрабатывать короткие имена, относительные элементы,и т.д ...).

Ответы [ 2 ]

2 голосов
/ 28 марта 2011

Я не верю, что в API есть удобная функция, чтобы ответить на этот вопрос для вас.Но я также не думаю, что слишком сложно написать надежную функцию для этого.Вот схема:

  1. Убедитесь, что Path1 и Path2 являются абсолютными путями.
  2. Проверьте, ссылаются ли Path1 и Path2 на один и тот же объект файловой системы (подробнее об этом ниже).
  3. Если это так, то ваша функция возвращает true.
  4. Если не убрать фамилию из Path2, т.е. удалить разделитель конечного пути (\ или /) и все, что за ним следует.
  5. Если на шаге 4 не удалось удалить какой-либо текст (например, не осталось разделителей пути), то вы достигли корневого уровня, и ваша функция вернула false.
  6. Перейти к 2.

СейчасКак проверить, что два имени относятся к одному и тому же объекту файловой системы.Самый безопасный способ сделать это - вызвать GetFileInformationByHandle() для обоих имен и сравнить dwVolumeSerialNumber, nFileIndexLow, nFileIndexHigh.Если все они равны, то два имени относятся к одному и тому же объекту.

Обратите внимание, что недостаточно сравнивать строки, поскольку один объект файловой системы может иметь много разных имен.Например, жесткие ссылки, символические ссылки, соединения, UNC против сопоставленных букв дисков и т. Д.

1 голос
/ 28 марта 2011

Вы можете использовать PathCommonPrefix , чтобы сравнить два пути для получения общего префикса.Затем сравните общий префикс с Path1 (ваш каталог).

Если они равны, то Path2 должен быть потомком.

Или вы можете уйти без использования буфера out и просто передать NULL для третьего параметра и проверить, что возвращаемое значение, которое является числом общих префиксных символов, равно Path1length.

Из примера документа PathCommonPrefix это не похоже на то, что PathCommonPrefix включает конечные разделители каталогов в префиксе 'common', поэтому вам придется удалить конечный sep вPath1 или откорректируйте сравнение результата соответственно из-за отсутствия завершающего sep.

...