2010-07-18 19 views
6

Estoy tratando de manejar rutas de archivos más largas en mi aplicación de Windows.C++ WinAPI: manejo de largas rutas de archivos/nombres

Actualmente, tengo un cuadro de texto (cuadro de edición) en el que un usuario puede escribir una ruta de archivo absoluta. luego leí que la ruta del archivo con tipo, utilizando GetWindowText, en una cadena declarada como tal: TCHAR FilePath[MAX_PATH];

Obviamente, aquí estoy confiando en la constante MAX_PATH que me limita a 260 caracteres. Entonces, para manejar nombres más largos de archivos/rutas podría ampliar mi matriz TCHAR así: TCHAR FilePath[32767];.

¿O hay una manera mejor? ¿Podría usar una matriz de longitud variable? (TCHAR FilePath[]; ¿es esto posible en C++? - lo siento, soy bastante nuevo en esto).

¡Gracias de antemano!


Aquí está todo el fragmento de código de lo que he mencionado anteriormente:

TCHAR FilePath[MAX_PATH]; 
ZeroMemory(&FilePath, sizeof(FilePath)); 
GetWindowText(hWndFilePath, FilePath, MAX_PATH); 
+3

Ese es exactamente el propósito de 'MAX_PATH' - no puede tener rutas más largas que eso. – casablanca

+0

@casablanca Sin embargo, podría ser una buena idea declararlo con MAX_PATH + 1 para el carácter final '\ 0'. – luiscubal

+0

@luiscabal: Acabo de comprobar [MSDN] (http://msdn.microsoft.com/en-us/library/aa365247%28VS.85%29.aspx#maxpath) y parece que MAX_PATH incluye el terminador nulo. – casablanca

Respuesta

11

Existen varias limitaciones con respecto a las rutas de archivos en Windows. De forma predeterminada, las rutas no pueden tener más de 260 caracteres, que es para lo que es la constante MAX_PATH.

Sin embargo, usted puede acceder a rutas más largas - con ciertas limitaciones - prefijando la ruta con "\\? \". Sin embargo, las limitaciones del uso del prefijo "\\ \?" Por lo general mayor que el beneficio:

  1. Hay una serie de API Win32 que no hay rutas de soporte con este prefijo (por ejemplo, LoadLibrary fallará siempre en una ruta que tiene más de 260 caracteres)
  2. Las reglas de Canonicalización de Win32 no surten efecto cuando se utiliza el prefijo "\\? \". Por ejemplo, de forma predeterminada, "/" en las rutas se convierte en "\", "." y ".." se convierten en referencias a los directorios actuales y principales respectivamente y así sucesivamente: nada de eso sucede cuando se usa el prefijo "\\? \".
  3. Solo porque puede modificar su programa para admitir rutas más largas, otros programas pueden no abrir los archivos que ha creado. Este será el caso si esos otros programas no también usan el prefijo "\\? \".

Para ser honesto, el punto # 2 es el verdadero asesino: se abre la puerta a todo tipo de problemas cuando se utiliza el prefijo "\\? \" Y que, básicamente, tiene que volver a poner en práctica el Canonicalización Win32 gobierna a sí mismo si vas por esa ruta

Por lo tanto, mi recomendación es seguir con la limitación de 260. Al menos hasta que haya un mejor soporte de plataforma para rutas más largas.

+0

Gracias por el consejo. ¡Creo que seguiré tu recomendación! – user353297

+0

Para el n. ° 2, tenga en cuenta que [GetFullPathNameW] (https://msdn.microsoft.com/library/aa364963) realiza esta canonicalización por usted, y ** no está ** limitado a MAX_PATH a menos que lo especifique como el tamaño del búfer. (Prefija la ruta con \\? \ Solo * después de * llamar a GetFullPathName.) Algunas advertencias restantes: 1) Las rutas UNC deben usar \\? \ UNC \ en lugar de \\. 2) Los dispositivos DOS como NUL o somedir \ NUL se convierten a \\. \ NUL, pero \\. \ No funciona en todas partes (y \\? \ UNC \. \ NUL es algo completamente diferente). 3) \\? \ C: \ NUL puede crear un archivo que es difícil de tratar. – Lexikos

-4

No, porque si le da una trayectoria más larga, Windows no puede aceptarlo. Entonces, aunque técnicamente, podría contener más caracteres que eso en su búfer, nunca podría usar el resultado del archivo.

5

Depende del tipo de programa que está escribiendo. Mi propia estrategia generalmente ha sido restringir la ruta creación a MAX_PATH de longitud, pero poder leer existente datos de rutas más largas (usando el prefijo "\? \" Que Dean menciona en su respuesta).Sin embargo, hay excepciones: por ejemplo, un programa de copia de seguridad debe aceptar rutas largas, y debe reproducir exactamente lo que se le dio como entrada.

Si bien es cierto que Dean es cierto que Windows no canonicaliza las rutas más largas para usted, tengo no consideró que esto era una gran preocupación como regla general. En general, esto no significa escribir su propio código para canonicalizar la ruta, generalmente significa que el usuario debe ingresar rutas de una manera que simplemente no genere tales cosas en primer lugar.