C++ 从路径中提取文件名

C++ 从路径中提取文件名,c++,arrays,pointers,double-pointer,C++,Arrays,Pointers,Double Pointer,好的,我有以下几点: wchar_t **filePathList; 它包含要添加到列表框的文件列表。问题是它们显示了整个文件路径,而我只想得到文件名。我考虑使用: wchar_t *tempChar; 从filePathList的末尾开始,然后返回到\。问题是我不能完全确定如何管理它。这是我目前掌握的代码: afx_msg void Send::OnDropFiles(HDROP hDropInfo) { if(uploadInProgress) { Mes

好的,我有以下几点:

wchar_t **filePathList;
它包含要添加到列表框的文件列表。问题是它们显示了整个文件路径,而我只想得到文件名。我考虑使用:

wchar_t *tempChar;
从filePathList的末尾开始,然后返回到
\
。问题是我不能完全确定如何管理它。这是我目前掌握的代码:

afx_msg void Send::OnDropFiles(HDROP hDropInfo)
{
    if(uploadInProgress)
    {
        MessageBox(L"Please wait for current upload to finish before adding files", L"Upload in progress", MB_OK);
        return;
    }

    int len;
    int prevNFiles = nFiles;
    wchar_t **buffer = filePathList;
    wchar_t *tempChar = NULL;

    // get number of files dropped into window
    nFiles += DragQueryFile(hDropInfo, 0xFFFFFFFF, NULL, 0);

    filePathList = (wchar_t**)malloc(nFiles*sizeof(wchar_t*));
    if(!filePathList)
    {
        MessageBox(L"FilePath list memory allocation failed", L"Error");
        nFiles = 0;
        if(buffer)
        {
            for(int i=0; i<prevNFiles; i++)
            {
                if(buffer[i]) free(buffer[i]);
            }
            free(buffer);
        }
        return;
    }
    memset(filePathList, 0, nFiles*sizeof(wchar_t*));

    // get file names
    for(int i=0; i<nFiles; i++)
    {
        if(i < prevNFiles)
        {   // previously entered files
            filePathList[i] = buffer[i];
            continue;
        }
        // newly dropped files
        len = DragQueryFile(hDropInfo, i-prevNFiles, NULL, 0)+1;    // 1 for \0
        tempChar = (wchar_t*)malloc(len*sizeof(wchar_t));
        filePathList[i] = (wchar_t*)malloc(len*sizeof(wchar_t));

        int index = len;

            // Attempting to iterate through the path to get the file name
        while(filePathList[i][index] != '\\')
        {
            tempChar = filePathList[index];
            index--;
        }

        filePathList[i] = tempChar;
        if(!filePathList[i])
        {
            MessageBox(L"FilePath memory allocation failed", L"Error");
            for(int j=0; j<i; j++)
            {
                if(filePathList[j]) free(filePathList[j]);
            }
            free(filePathList); filePathList = NULL;
            nFiles = 0;
            break;
        }
        len = DragQueryFile(hDropInfo, i-prevNFiles, filePathList[i], len);

    }

    if(buffer) free(buffer);

    // display files
    UpdateFileListDisplay();
}
afx\u msg void Send::OnDropFiles(HDROP-hDropInfo)
{
如果(上载进程)
{
MessageBox(L“请等待当前上传完成后再添加文件”,L“正在上传”,MB_OK);
返回;
}
内伦;
int prevNFiles=nFiles;
wchar\u t**buffer=文件路径列表;
wchar_t*tempChar=NULL;
//获取拖放到窗口中的文件数
nFiles+=DragQueryFile(hDropInfo,0xFFFFFFFF,NULL,0);
filePathList=(wchar\u t**)malloc(nFiles*sizeof(wchar\u t*));
如果(!filePathList)
{
MessageBox(L“文件路径列表内存分配失败”,L“错误”);
nFiles=0;
if(缓冲区)
{

对于(int i=0;i而言,错误在该位代码中:

tempChar = (wchar_t*)malloc(len*sizeof(wchar_t));
filePathList[i] = (wchar_t*)malloc(len*sizeof(wchar_t));

int index = len;

// Attempting to iterate through the path to get the file name
while(filePathList[i][index] != '\\')
{
    tempChar = filePathList[index];
    index--;
}
这里有几个问题:

  • len
    不包含空终止符,因此您没有分配足够的内存。您还需要一个字符
  • 第二次调用
    DragQueryFile
    填充缓冲区失败
  • 您对
    filePathList[i][index]
    的首次访问超出了范围,因为
    index
    超出了数组的末尾
  • 由于
    filePathList[i]
    未初始化,循环可能会倒计时到
    index
    为0,然后产生访问冲突
  • 即使修复了所有这些错误,也需要在循环中测试
    索引>=0
    ,以防字符串不包含路径分隔符
  • 在你的问题中,我没有看过任何其他代码,但我敢打赌,我没有发现所有的错误。这应该足够了


    Joachim建议使用
    \u splitpath
    非常合理,但另一方面,您确实需要掌握这种类型的编码。

    错误在于这段代码:

    tempChar = (wchar_t*)malloc(len*sizeof(wchar_t));
    filePathList[i] = (wchar_t*)malloc(len*sizeof(wchar_t));
    
    int index = len;
    
    // Attempting to iterate through the path to get the file name
    while(filePathList[i][index] != '\\')
    {
        tempChar = filePathList[index];
        index--;
    }
    
    这里有几个问题:

  • len
    不包含空终止符,因此您没有分配足够的内存。您还需要一个字符
  • 第二次调用
    DragQueryFile
    填充缓冲区失败
  • 您对
    filePathList[i][index]
    的首次访问超出了范围,因为
    index
    超出了数组的末尾
  • 由于
    filePathList[i]
    未初始化,循环可能会倒计时到
    index
    为0,然后产生访问冲突
  • 即使修复了所有这些错误,也需要在循环中测试
    索引>=0
    ,以防字符串不包含路径分隔符
  • 在你的问题中,我没有看过任何其他代码,但我敢打赌,我没有发现所有的错误。这应该足够了


    Joachim建议使用
    \u splitpath
    非常合理,但另一方面,您确实需要掌握这种类型的编码。

    您正在使用的函数与编写的函数一样长76行。这并不是灾难性的长,但已经到了难以推理的地步。可能值得将将函数分解为几个较小的函数。您正在解决的一个问题是如何从完整路径中提取文件名。您可以编写一个具有以下签名的函数:

    char *filename_from_path(const char *fullpath);
    
    这将接收完整路径并返回一个仅包含文件名的新字符串。(注意:您必须小心谁分配和释放文件名字符串)。分解这样一个函数的巧妙之处在于,对于如何执行小的子部分,通常有很好的建议:

    例如


    分离出该逻辑将使您更容易对正在处理的较大循环进行推理。

    您正在处理的函数的长度为76行。这并不是灾难性的长,但已经到了难以推理的地步。将该函数分离为几个小循环可能是值得的er函数。您正在解决的一个问题是如何从完整路径中提取文件名。您可以编写带有签名的函数,如:

    char *filename_from_path(const char *fullpath);
    
    这将接收完整路径并返回一个仅包含文件名的新字符串。(注意:您必须小心谁分配和释放文件名字符串)。分解这样一个函数的巧妙之处在于,对于如何执行小的子部分,通常有很好的建议:

    例如


    分离该逻辑将使您更容易对正在处理的较大循环进行推理。

    您也可以打开该文件以查找其名称。尽管这可能与通过路径一样慢。

    您也可以打开该文件以查找其名称。尽管这可能与通过路径一样慢通过路径。

    你能使用吗?为什么人们对此投反对票?可能是因为提出问题的人尝试过(显然失败了)做一些有标准功能的事情?是的,我尝试过,但失败了。但我不知道这有标准功能。正如我所说的,我仍然是新的和正在学习的。@Joachim我们不应该因为人们知道的比我们使用的要少而否决他们?为什么人们否决这个?可能是因为问问题的人n尝试过(显然失败了)做一些有标准功能的事情?是的,我尝试过,但失败了。但我不知道有标准功能。正如我所说的,我仍然是新的和正在学习的。@Joachim我们不应该否决人们,因为他们知道的比我们知道的少。这真的不是做这件事的方式。对不起。这真的不是做这件事的方式。对不起。所有的在我尝试只获取文件名之前,这其中的一个功能已经发挥了作用