Индекс был вне диапазона после удаления нескольких строк из таблицы данных? C # - PullRequest
0 голосов
/ 31 августа 2018

Я использую ArrayList для бинарного поиска. Строки datagridview добавляются в ArryList. Когда я удаляю одну строку из таблицы данных, она работает почти идеально. Проблема в том, что когда я удаляю много строк из таблицы данных сверху или снизу и посередине, это выдает ошибку. Как я могу обновить или обновить ArrayList после удаления строки из ArrayList (datagridview)?

Ошибка:

'Индекс был вне диапазона. Должен быть неотрицательным и меньшим, чем размер коллекции. Имя параметра: индекс '


Мой код для копирования строк в ArrayList:

Я поместил этот код в событие кнопки MouseEnter, поэтому, прежде чем нажать кнопку, чтобы выполнить поиск, он копирует все в ArrayList.

foreach (var row in dataGridView2.Rows.Cast<DataGridViewRow>())
{
   ArrayList[row.Index] = row.Cells[0].Value.ToString().Trim();
}

Мой код удаления для выбранных строк:

foreach (DataGridViewRow item in this.dataGridView2.SelectedRows)
{
    dataGridView2.Rows.RemoveAt(item.Index);
    return;
}

Мой код для бинарного поиска в winform:

int index = this.ArrayList.BinarySearch(textBoxBinarySearch.Text);
if (index > -1)
{
    dataGridView2.SelectionMode = DataGridViewSelectionMode.RowHeaderSelect;
    dataGridView2.Rows[index].Selected = true;
    dataGridView2.CurrentCell = dataGridView2.Rows[index].Cells[0];
    MessageBox.Show("Index is equal to: " + index, "Binary Search");
}

Ошибка происходит в:

dataGridView2.Rows[index].Selected = true;

После открытия csv бинарный поиск работает отлично!

Проверка функции удаления.

enter image description here

Удалено больше строк из таблицы данных.

enter image description here

После удаления многих строк из таблицы данных, если я пытаюсь найти имя, появляется сообщение об ошибке.

enter image description here


Надеюсь, я не пропустил информацию из моего описания. Спасибо, если вы прочитали это через!

Ответы [ 3 ]

0 голосов
/ 31 августа 2018

Я нашел быстрый способ сделать это:

public partial class Form1 : Form
{
    public Form1()
    {
        InitializeComponent();

        PopulateGrid();
    }

    private ArrayList myList = new ArrayList();
    private List<Student> students = new List<Student>();

    private void PopulateGrid()
    {
        students = new List<Student>
        {
            new Student {Lastname = "aa"},
            new Student {Lastname = "bb"},
            new Student {Lastname = "cc"},
            new Student {Lastname = "cc"},
            new Student {Lastname = "cc"},
            new Student {Lastname = "ee"},
            new Student {Lastname = "ff"},
            new Student {Lastname = "ff"},
            new Student {Lastname = "gg"},
            new Student {Lastname = "gg"},
        };

        dataGridView2.DataSource = students;
        myList = new ArrayList(students.Select(x => x.Lastname).ToList());
    }

    public class Student
    {
        public string Lastname { get; set; }
    }

    private void btnSearch_Click(object sender, EventArgs e)
    {
        var index = myList.BinarySearch(textBoxBinarySearch.Text);
        if(index > -1)
        {
            dataGridView2.SelectionMode = DataGridViewSelectionMode.RowHeaderSelect;
            dataGridView2.Rows[index].Selected = true;
            dataGridView2.CurrentCell = dataGridView2.Rows[index].Cells[0];
            MessageBox.Show("Index is equal to: " + index, "Binary Search");
        }
    }

    private void btnDelete_Click(object sender, EventArgs e)
    {
        if (dataGridView2.SelectedRows.Count > 0)
        {

            var selected = dataGridView2.SelectedRows[0];
            students.RemoveAt(selected.Index);

            dataGridView2.DataSource = null;
            dataGridView2.DataSource = students;
            myList = new ArrayList(students.Select(x => x.Lastname).ToList());
        }
    }
}

Но я бы посоветовал избегать использования ArrayList, так как это не сильный тип. Вместо этого используйте List<T>. Я предполагаю, что причиной использования ArrayList является BinarySearch метод.

0 голосов
/ 01 сентября 2018

Я использую ArrayList для бинарного поиска. Строки datagridview добавлен в ArryList. Когда я удаляю одну строку из datagridview, это работает почти идеально. Проблема в том, когда я удаляю много строк из сетки данных сверху или снизу и посередине, это дает мне ошибку. Как я могу обновить или обновить ArrayList после того как я удалил строку из ArrayList (datagridview)?

Решение:

Когда я дважды возражал против файла csv, бинарный поиск работал хорошо, но в третий раз - нет, потому что мне пришлось очистить ArrayList с помощью ArrayList.Clear();, а не только сеткой данных. Затем я мог бы скопировать строки таблицы данных в пустую ArrayList.

dataGridView2.Rows.Clear();
ArryList.Clear();

Тогда ->

Мой код для копирования строк в ArrayList:

Я поместил этот код в событие кнопки MouseEnter, поэтому, прежде чем нажать кнопку, чтобы выполнить поиск, он копирует все в ArrayList.

foreach (var row in dataGridView2.Rows.Cast<DataGridViewRow>())
{
   ArrayList[row.Index] = row.Cells[0].Value.ToString().Trim();
}

Мой код удаления для выбранных строк:

for (int i = dataGridView2.SelectedRows.Count - 1; i >= 0; i--)
{ 
      dataGridView2.Rows.RemoveAt(dataGridView2.SelectedRows[i].Index);
      ListOfPeople.RemoveAt(i);
}

Мой код для бинарного поиска в winform:

int index = this.ArrayList.BinarySearch(textBoxBinarySearch.Text);
if (index > -1)
{
    dataGridView2.SelectionMode = DataGridViewSelectionMode.RowHeaderSelect;
    dataGridView2.Rows[index].Selected = true;
    dataGridView2.CurrentCell = dataGridView2.Rows[index].Cells[0];
    MessageBox.Show("Index is equal to: " + index, "Binary Search");
}

Спасибо, если вы прочитали это через!

0 голосов
/ 31 августа 2018

Похоже, проблема заключается в том, что вы удаляете только элементы из DataGridView, но не из ArrayList, а затем используете индекс поиска arraylist для DataGridView. Таким образом, если вы удалите последний элемент из DataGridView, он все еще существует в ArrayList, поэтому, если вы сопоставите этот элемент и попытаетесь использовать индекс в DataGridView, вы получите индекс вне диапазона исключений.

Если у вас есть 10 элементов в списке массивов и в представлении сетки данных, то удалите 2 из вида сетки данных, теперь у вас есть 10 элементов в списке массивов и 8 в виде сетки данных. Если вы получите индекс одного из последних 2 элементов в массиве списков (8 или 9) и попытаетесь получить доступ к элементам в этих признаках в представлении данных, это вызовет исключение.

Попробуйте вместо этого использовать привязку данных, а затем работать только с ArrayList.

dataGridView2.DataSource = ArrayList;

Кроме того, если вы перебираете список, удаляя элементы, делайте это задом наперед. Начните с элемента с последним элементом и вернитесь к началу:

for(int i = dataGridView2.SelectedRows.Count - 1 ; i >= 0 ; i--)
{
    dataGridView2.Rows.RemoveAt(dataGridView2.SelectedRows[i].Index);
}

Выполнение foreach заставляет перечислитель генерировать исключение, поскольку список меняется с одного прохода на следующий.

...