2016-08-15 6 views
0

У меня возникли проблемы с использованием Disable/EnableControls(), итерации по DataSet, а именно при обновлении полей.Проблема с отправкой правильных данных с помощью disablecontrols

Кажется, что происходит с двумя обновленными полями, заключается в том, что все они принимают одни и те же данные. Похоже, последнее значение для сообщения вводится для всех строк. Так что давайте скажем, что у нас есть 3 записи, которые обновили значения 1, 2 и 3 (в моем случае 3 публикуются для всех полей), когда я ожидал 1, 2 и 3 для последнего поля.

Например, у меня есть 10 записей, которые находятся в моем наборе данных. Я запускаю эту функцию, смотря на сетку и сохраняя данные, значение столбца Cost одинаково для каждой строки, даже если я перешагнул и поместил часы на функцию getNewDataValue, и они будут разными значениями.

NumberSelected = 0; 
dataSourceItems.DataSet.DisableControls; //it this be my problem, accessing the dataset via the datasource? – I tried this and it didn’t make a difference. 
while (NumberSelected < cxGridDBTableView1.Controller.SelectedRowCount) do 
begin 
    Id = cxGridDBTableView1.Controller.SelectedRows[NoSelected]).Values[0]; 
    if dataSourceItems.DataSet.locate('PK', Id, []) then 
    begin 
    dataSourceItems.DataSet.edit; 
    dataSourceItems.DataSet.fieldbyname('Cost').asfloat := getNewDataValue; 
    dataSourceItems.DataSet.Post; 
    inc(NumberSelected) 
    end; 

    dataSourceItems.DataSet.EnableControls; 
end; 

Я использую Delphi 2010, DevExpress Quantum Grid, и FIBPlus наборы данных, доступ к Firebird базы данных.

Глядя на документацию, я могу видеть, что, когда DisableControls() называется, TDataSet.DataEvent не проходит события DataSources, и что все мастер-деталь отношения разрываются, пока EnableControls() не называется. Может ли быть доступ к DataSet в DataModule через DataSource? Я пробовал это, и это не имеет значения.

Без использования Disable/EnableControls() скорость непригодна. Таким образом, любой совет или альтернативный способ итерации по большому набору данных по скорости будет полезен.

+0

Вы не должны полагаться (как вы в данный момент) на изменение их размещения в наборе данных, прежде чем ее строка-курсор перемещается , Явно вызовите dataSourceItems.DataSet.Post сразу после назначения fieldbyname(). Попробуйте это - он может решить вашу проблему сам по себе, но вы все равно должны это делать. – MartynA

+0

Отредактировал мой вопрос для ясности, поскольку я фактически не вызывал вызов для сообщения явно. Ваше право, я изменюсь и испытаю сейчас. – MrRobot

+0

Получите тот же результат даже после публикации сразу после назначения fieldbyname(). – MrRobot

ответ

4

Вы звоните EnableControls() от внутри цикл, когда он должен быть вне цикл вместо (предпочтительно в try..finally блоке).

Но что более важно, вы не увеличиваете NoSelected, так что вы всегда получаете доступ к одному и тому же выбранному идентификатору каждый раз, когда вы делаете редактирование. У вас есть две переменные, которые борются за выполнение задания, которое одна переменная должна выполнять сама по себе.

Попробуйте вместо этого:

NumberSelected = 0; 
dataSourceItems.DataSet.DisableControls; 
try 
    while (NumberSelected < cxGridDBTableView1.Controller.SelectedRowCount) do 
    begin 
    Id = cxGridDBTableView1.Controller.SelectedRows[NumberSelected]).Values[0]; 
    if dataSourceItems.DataSet.Locate('PK', Id, []) then 
    begin 
     dataSourceItems.DataSet.Edit; 
     dataSourceItems.DataSet.FieldByName('Cost').AsFloat := getNewDataValue; 
     dataSourceItems.DataSet.Post; 
    end; 
    Inc(NumberSelected); 
    end; 
finally 
    dataSourceItems.DataSet.EnableControls; 
end; 

В качестве альтернативы:

dataSourceItems.DataSet.DisableControls; 
try 
    for NumberSelected = 0 to cxGridDBTableView1.Controller.SelectedRowCount-1 do 
    begin 
    Id = cxGridDBTableView1.Controller.SelectedRows[NumberSelected]).Values[0]; 
    if dataSourceItems.DataSet.Locate('PK', Id, []) then 
    begin 
     dataSourceItems.DataSet.Edit; 
     dataSourceItems.DataSet.FieldByName('Cost').AsFloat := getNewDataValue; 
     dataSourceItems.DataSet.Post; 
    end; 
    end; 
finally 
    dataSourceItems.DataSet.EnableControls; 
end;