0

了解しました。次の情報があります。

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();
}

問題は、VisualStudioがtempCharを「不良ptr」として報告していることです。私はプログラミングに関してはまだ本当に環境に配慮していて、ポインターについてはほとんど知らず、ダブルポインターについてはほとんど知らないことを認めます。しかし、どんな助けでも大歓迎です。ありがとうございました。

4

3 に答える 3

3

使用している関数は、記述されている限り76行です。それは壊滅的なほど長くはありませんが、推論するのが難しいところまで来ています。この関数をいくつかの小さな関数に分割することはおそらく価値があります。あなたが取り組んでいる問題の1つは、フルパスからファイル名を抽出する方法です。次のようなシグネチャを使用して関数を記述できます。

char *filename_from_path(const char *fullpath);

これはフルパスを取り、ファイル名だけで新しい文字列を返します。(注:ファイル名文字列を誰が割り当てて解放するかについて注意する必要があります)。そのような関数を分解することについての素晴らしいことは、小さなサブピースを実行する方法についてしばしば良いアドバイスがあるということです:

たとえば、 MSVS2005を使用してCのフルパスからファイル名を抽出します

そのロジックを分離すると、作業中のより大きなループについて推論しやすくなります。

于 2011-12-20T21:06:56.420 に答える
1

エラーは次のコードにあります。

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--;
}

ここでいくつかの問題:

  1. lennullターミネータが含まれていないため、十分なメモリが割り当てられていません。もう1文字必要です。
  2. DragQueryFileバッファを埋めるために2回目の呼び出しに失敗しました。
  3. は配列の終わりを超えているため、の最初のアクセスはfilePathList[i][index]範囲外です。index
  4. 初期化されていないためfilePathList[i]、ループはおそらくindex0までカウントダウンし、アクセス違反を生成します。
  5. これらのエラーをすべて修正しindex>=0た場合でも、文字列にパスセパレータが含まれていない場合は、ループでテストする必要があります。

私はあなたの質問で他のコードを見たことがありませんが、私はすべてのエラーを見つけたわけではないことを確信しています。今のところこれで十分です。

Joachimの使用に関するアドバイス_splitpathは非常に適切ですが、逆に言えば、このタイプのコーディングをマスターする必要があります。

于 2011-12-20T20:58:32.770 に答える
0

ファイルを開いて名前を見つけることもできます。それはおそらく道を進むのと同じくらい遅いですが。

于 2011-12-20T21:19:41.760 に答える