Главная страница
Top.Mail.Ru    Яндекс.Метрика
Текущий архив: 2010.09.26;
Скачать: CL | DM;

Вниз

Как исправить поле "счётчик"? (ADO + Access)   Найти похожие ветки 

 
_MiK_   (2010-06-26 09:52) [0]

Случайным образом, после длительной эксплуатации ADO + Access, в таблице была обнаружена ошибка - поле "счётчик" перестало быть ключевым. Сделать его обратно таковым - не давали несколько повторяющихся чисел. Помогло только удаление этого поля (т.к. исправить номер записи нельзя), и создание его заново.
Как программно:
- обнаружить данную ошибку?
- исправить (переиндексировать) значения данного поля?


 
sniknik ©   (2010-06-26 12:03) [1]

> поле "счётчик" перестало быть ключевым.
поле "счётчик" и не обязано быть ключевым... просто чаще всего используется в этой связке для суррогатных ключей.
т.что если кто-то(???) поменял структуру таблицы, аксесс(jet) сопротивляться не будет. программисту типа виднее какая ему структура нужна.

> Как программно:
> - обнаружить данную ошибку?
95% системных ошибок сидят в 30-40 см перед монитором...

> - исправить (переиндексировать) значения данного поля?
удалить дубли (или записать новую последовательность, если удалять нельзя), восстановить ключ - alter table ..., установить желаемое значение счетчика - alter table ....


 
sniknik ©   (2010-06-26 12:09) [2]

> или записать новую последовательность, если удалять нельзя
естественно изменив предварительно тип на простой интежер (alter table ...), и возможно даже не восстанавливать последовательность (если не критично, нет связок на этот ключ)  а просто "занилить" все, при смене типа на счетчик оно вроде само считает.


 
_MiK_   (2010-06-26 12:59) [3]

1) на счёт обнаружения ошибки в базе - я думаю самое простое, это проверить является ли первое поле ID в таблице - ключевым? Как это можно проверить программно?
2) благодарю за подсказку! только хотел уточнить:
- меняем тип поля на Integer:
alter table [название таблицы] alter column ID Integer
- очищаем:
Update [название таблицы] Set ID = NULL
Как заполнить поле заново (числами по-порядку)? Какое значение соответствует типу поля "счётчик", чтобы потом из Integer его обратно сметнить? И как его сделать ключевым?


 
sniknik ©   (2010-06-26 13:41) [4]

> Как заполнить поле заново (числами по-порядку)?
> а просто "занилить" все, при смене типа на счетчик оно вроде само считает.

> Какое значение соответствует типу поля "счётчик"
справочную информацию без проблем можно получить в справке...

> И как его сделать ключевым?
> восстановить ключ - alter table ...


 
_MiK_   (2010-06-26 15:20) [5]

Ок! - спасибо!
А на счёт первого вопроса - является ли первое поле ID ключевым?
Как проверить?


 
Ega23 ©   (2010-06-26 15:26) [6]


> является ли первое поле ID ключевым?


Обратиться к INFORMATION_SCHEMA


 
sniknik ©   (2010-06-26 16:19) [7]

а смысл?
само по себе поле не меняет тип/не становится не ключевым. это сделал ты (твоя программа) судя по неуемному желанию, даже при ошибке, восстанавливать и  менять структуру только программно...

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


 
_MiK_   (2010-06-26 20:51) [8]

Итак...
1) "Побились" индексы в двух подчинённых таблицах. Их изменение ни на что не влияет (не привязаны ни к чему). Как бьются? - можно только догадываться... м.б. сеть, или одновременное создание двух записей! Поля "счётчики" в них я может бы и не делал, но почитав умные книги - понял, что ключевое поле обязательно должно быть в любой таблице. Или можно без них?

2) Не сработало (или я не правильно делаю):
ADOConnection.OpenSchema(siPrimaryKeys, VarArrayOf([Unassigned, Unassigned,
    "TablePL"]), EmptyParam, ADODataSetPL);

ADODataSetPL.RecordCount всегда = -1

3) Опусташённый alter column ID Integer => Set ID = NULL делать счётчиком не даёт - пишет, что необходимо создать новое поле. Значит нужно удалять/создавать поле ID? или, как я уже спрашивал - можно перезаполнить Integer и попробовать его сделать AutoInc?


 
Anatoly Podgoretsky ©   (2010-06-26 21:45) [9]

Можно без ПК, но он обязательно должно быть.


 
sniknik ©   (2010-06-26 23:55) [10]

> alter column ID Integer => Set ID = NULL
это что за бред? пиши по русски. в смысле в командах sql.

> Значит нужно удалять/создавать поле ID?
как хочешь, но голос разума за то чтобы не трогать структуру базы в процессе эксплуатирования. (коней на переправе не меняют. а если уж и меняют то тщательно взвесив и обдумав все, и уж точно не автоматом в программе)

> можно перезаполнить Integer и попробовать его сделать AutoInc?
можно, попробуй.

проблема только в том, что основное предназначение ПК это однозначная, по нему, идентификация записи... и назначить полностью одинаковым по значениям записям разные ID ты не сможешь, запросом естественно. т.к. при отсутствии ПК идентификация затруднена, и неважно, что это для восстановления ПК и делается.


 
_MiK_   (2010-06-27 07:22) [11]

>пиши по русски. в смысле в командах sql.
Я же написал ранее:
- меняем тип поля на Integer:
alter table [название таблицы] alter column ID Integer
- очищаем:
Update [название таблицы] Set ID = NULL

Всё срабатывает! А вот обратно - в AutoInc не делается (не заполняется автоматом), пишет, что нужно создать новое поле.

>не трогать структуру базы в процессе эксплуатирования
Фактически она остаётся такой, как была. Не могу же я оставить таблицу с битым полем. Вручную помогло только удаление этого поля, и добавление его-же заново (первым, с тем-же именем). Пусть числа (номера) поменялись, как я ранее написал - к ним у меня ничего не привязано, добавлено просто для наличия в таблице ключевого поля - т.к. остальные для этого не подходят (могут повторяться).
Один раз ладно - можно исправить и вручную, но в дальнейшем хотелось бы, чтобы наличие ошибки определялось автоматически, но, к сожалению:
>Не сработало (или я не правильно делаю):
ADOConnection.OpenSchema(siPrimaryKeys, VarArrayOf([Unassigned, Unassigned,
   "TablePL"]), EmptyParam, ADODataSetPL);
ADODataSetPL.RecordCount всегда = -1

и автоматически исправлялось.
>назначить полностью одинаковым по значениям записям разные ID ты не сможешь, запросом естественно
Тогда подскажите  - как?


 
sniknik ©   (2010-06-27 12:00) [12]

> но в дальнейшем хотелось бы, чтобы наличие ошибки определялось автоматически
еще раз повторю, это НЕ ОШИБКА, это то как ты спроектировал/сделал структуру изначально, раз уж говоришь не менял ее. использовать можно и так и так, в зависимости от пожелания программиста.
и раз уж сейчас переделал вручную, то такой она и останется.

> и автоматически исправлялось.
вот это, если реализуешь, будет ОШИБКА! т.к. при малейшей неточности ты так исковеркаешь данные, что их невозможно будет восстановить.

> Тогда подскажите  - как?
легко. табличными методами jet/dao напрямую.


 
sniknik ©   (2010-06-27 12:03) [13]

кстати раз получается удалением/созданием поля и на значения тебе плевать, то почему просто это не реализовать да и все?


 
Anatoly Podgoretsky ©   (2010-06-27 13:21) [14]

> sniknik  (27.06.2010 12:03:13)  [13]

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


 
_MiK_   (2010-06-29 16:36) [15]

Извиняюсь - проблемы с Интернетом!

>это то как ты спроектировал/сделал структуру изначально
Я спроектировал изначально первое поле - счётчик, ключевое! После нескольких сбоев и сжатий/восстановлений обнаружилось описываемое выше. Не было предусмотренно менять структуру таблицы! Более того - где Вы видели поле счётчик, с дублями (двумя одинаковыми номерами)? Если даже захотеть - такое программно ни сделать.

Как исправил? - вручную удалил из битой таблицы (в режиме "Конструктора" таблицы в Access) поле счётчик, переставшее быть ключевым. Затем добавил новое первое поле - ключевое, счётчик. Он спросил что-то вроде: "пронумеровать?" - "да." Всё - ОК! И базой снова стали нормально пользоваться. Номер в поле счётчик меня не волнует - оно мне нужно исключительно для запросов UPDATE. Данное поле ни с какой другой таблицей не связано. Всё работает!

Теперь - как организовать профилактику возникновения таких ошибок? Как их вычислить  - я придумал: запросом SELECT + COUNT я проверяю поле "Номер" на наличие дублей. А вот - как исправить? - не придумаю никак.
Основной вопрос - поле счётчик - как описать этот тип в запросе ALTER TABLE? Я выяснил, что это - длинное целое (в access - Long), с дополнениями. Но какими? Как указать в запросе - свойство поля "последовательное"?

И ещё одно - при добавлении поля, в конце запроса пишу - FIRST, поле добавляется, но последним, а не первым, как этго хотелось бы.


 
sniknik ©   (2010-06-29 16:58) [16]

> Если даже захотеть - такое программно ни сделать.
не шути так
->
CREATE TABLE CountTable (ID Counter, Name VarChar(30))
INSERT INTO CountTable (ID,Name) VALUES (1, "Test")
INSERT INTO CountTable (ID,Name) VALUES (1, "Test")
INSERT INTO CountTable (ID,Name) VALUES (1, "Test")

> поле счётчик, переставшее быть ключевым.
оно не может перестать быть ключевым... сколько раз повторять? и нужно не профилактику делать, а исключать методы приводящие к изменению структуры.
которые у тебя могли быть например тут

> После нескольких сбоев и сжатий/восстановлений
если делал восстановление копированием в другую базу например, или (чем черт не шутит) через mssql (ну да весело, но...) он может сбросить т.к. не всегда обращает внимание на ключи/индексы вроде тоже, не помню, могут "потеряться".

> И ещё одно - при добавлении поля, в конце запроса пишу - FIRST, поле добавляется, но последним, а не первым, как этго хотелось бы.
что за бред?


 
sniknik ©   (2010-06-29 17:51) [17]

кстати чем можно довести базу access до нескольких восстановлений? у меня за 10 лет работы с больше 10 тыс инсталляций, вспоминается 3 максимум 4 сбоя. а тут с одной базой несколько, чудеса...


 
Palladin ©   (2010-06-30 10:17) [18]

чудеса в 30-40 см перед монитором )



Страницы: 1 вся ветка

Текущий архив: 2010.09.26;
Скачать: CL | DM;

Наверх




Память: 0.53 MB
Время: 0.008 c
2-1278147722
SIV5000
2010-07-03 13:02
2010.09.26
PNG + Componenet;


15-1277806505
ficus
2010-06-29 14:15
2010.09.26
Творческий кризис


2-1277971578
Nickolay
2010-07-01 12:06
2010.09.26
Русификация


15-1277748407
@!!ex
2010-06-28 22:06
2010.09.26
Проблема с заданием полей таблицы в Lua


2-1278137781
linuxoid
2010-07-03 10:16
2010.09.26
как загрузить данные из access в treeview?