Pergunta

Eu tenho um formulário que contém um componente TOpenDialog (OpenDialog1) e um botão. OpenDialog1 tem a ofAllowMultiSelect (de Options) conjunto de propriedades como true.

Ao clicar no botão AddFilesToListView método é executado:

procedure TForm4.AddFilesToListView();
var
  ListItem : TListItem;
  I: Integer;
  F : File;
  LengthOfAudio : TDateTime;
  previousCursor : TCursor;

begin
  previousCursor := Self.Cursor;
  Self.Cursor := crHourGlass;

  if OpenDialog1.Execute then
  begin
    for I := 0 to OpenDialog1.Files.Count - 1 do begin
      if FileExists(OpenDialog1.FileName) then begin
        ListItem:=ListView1.Items.Add;
        ListItem.Caption := 'Test';
        ListItem.SubItems.Add(ExtractFileName(OpenDialog1.Files[I]));
        ListItem.SubItems.Add(ExtractFilePath(OpenDialog1.Files[I]));
      end else
        raise Exception.Create('File does not exist.');
    end;
  end;

  Self.Cursor := previousCursor;

  OpenDialog1.Files.Free;
end;

Ao executar o aplicativo, selecionando o primeiro arquivo, eu não tenho nenhum problema, mas quando se quer seleccionar o segundo, eu recebo um erro dizendo "Projeto project3 levantou uma classe de exceção EInvalidPointer com a mensagem 'ponteiro inválido Operação'."

O que é a causa desta, como faço para corrigir isso?

Foi útil?

Solução

significa "operação ponteiro inválido" você libertou memória que não pertence a você. Uma dessas três coisas é a causa:

  • O seu programa libertou algo que já havia sido libertado antes.
  • O seu programa libertou algo que nunca foi alocado em primeiro lugar.
  • O seu programa libertou algo que tinha sido atribuída com um gerenciador de memória diferente.

Em seu código, você está liberando propriedade TOpenDialog do Files. Você não alocar essa lista corda, ea documentação não lhe diz para libertá-la, por isso é razoável esperar que a lista na verdade pertence ao componente de diálogo, e que o componente irá libertá-la quando quiser. Verificar o código-fonte em Dialogs.pas , confirma isso. Desde que você também ter liberado esse objeto, você tem um erro de double-free, que se encontra com o primeiro critério que listei acima. Remover essa linha.

Como Uwe apontou , você está também o processamento de um lista de nomes de arquivos, mas apenas verificar a existência de um. Isso é um erro de lógica em seu programa, mas não causaria a exceção que você está vendo.

Outras dicas

Você deve verificar se há

if FileExists(OpenDialog1.Files[I]) then begin

em vez de

if FileExists(OpenDialog1.FileName) then begin

Melhor investir em uma variável local segurando esse valor.

E por que isso?

OpenDialog1.Files.Free;

Os arquivos é propriedade do o TOpenDialog, e não deve ser liberado diretamente.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top