Конференція vbstreets - перегляд теми - дерево в access 2018

iGrok писал (а): А якщо малася на увазі структура даних - тут взагалі варіантів маса.

Один з найпростіших:
Element_ID, Parent_ID, Element_Name

Parent_ID - ID елемента-батька. Якщо Parent_ID = 0 - елемент знаходиться "в корені" дерева.

Так у мене тільки одна таблиця виходить. А що робити з 4-ма довідниками?

Я правильно зрозумів структуру?

Департаменти -> Відділи -> Сектори -> Посади -> Человеки.

З поточної структурою, якщо дані внутрішньо несуперечливі, дерево побудувати можна, але досить важко буде підтримувати ту саму несуперечливість при змінах.

Або у тебе теоретично можливий варіант, коли один відділ виявиться в двох департаментах?

Якщо важливо зберегти стуктуру даних незмінною - можна спробувати будувати дерево по "Штатному розкладом".
Зробити вибірку: SELECT DISTINCT depart, otd, sek, dolj FROM [Штатний розклад] ORDER BY depart, otd, sek, dolj
Потім йти по записах, і додавати в дерево департаменти, відділи, секції та посади.
Тобто для кожного запису перевіряти, чи є вже в корені дерева такої департамент, якщо немає - додавати. Потім так само з відділом, але дивитися його вже не в корені, а в поточному департаменті, і т.п. вполть до посади.

Такий спосіб побудови дерева може виявитися досить повільно, але як реалізувати щось більш ефективне, не змінюючи структуру БД я не знаю. Можу тільки підказати підходящий варіант зміни структури.

label:
cli
jmp label

Щодо структури даних, думаю ти хотів запропонувати дописати до таблиць

Element_ID, Parent_ID, Element_Name
Parent_ID - ID елемента-батька. Якщо Parent_ID = 0 - елемент знаходиться "в корені" дерева.

О, я вже уявив собі, як це може виглядати: спочатку є список (запит на вибірку, обедіняющій union'амі все довідники в один список). але виводиться він уже в TreeView (тобто, кожен елемент - це корінь дерева), потім, поруч зі списком комбобокс, в якому окремо вибрані найменування. при виборі елемента зі списку ми бачимо в комбо 0 або напис "немає" - це означає, що елемент є кореневим. тепер ми вибираємо в комбо зі списку потрібний нам елемент і його ID записується в Parent_ID поточного елемента, після чого оновлюємо дерево (процедуру поновлення треба оптимізувати максимально, щоб не гальмувало, або оновлювати не автоматично, а після натискання на кнопку), отже, в дереві з'являється перша гілка.

Всю процедуру повторюємо до переможного кінця!

Саму форму можна так і обізвати: Довідник Відділів.
_________________

І так! Дуже зручно для представлення дерева зробити таблицю зв'язків. ось так вона повинна виглядати:
Код: Виділити все ID
Департамент_ID,
Отдел_ID,
Сектор_ID,
Должность_ID,
Сотруднік_ID
У кожного запису цієї таблиці буде прописана кожна одна зв'язок будь-якого елементу одного довідника з будь-яким елементом іншого або декількох. На основі цієї таблиці і будувати дерево.

По суті, така таблиця у smitatyana вже наполовину реалізована в таблиці штатного розкладу, але це неправильно. Потрібно в штатному залишити тільки поле з номером (ID) записи в таблиці зв'язків.

При такому розкладі Parent_ID взагалі не потрібні! Структура-то жорстка. У сектора безпосереднім Паренте може бути тільки відділ. У співробітника тільки посаду (щоб дізнатися з якого від відділу, сектору, департаменту це теж вказано в запису)
якщо у одного співробітника дві посади (внутрішній сумісник) то в таблиці зв'язків на нього буде заведено відповідно два записи.

Програмування - богообрана дисципліна! Якщо бог і є, то всесвіт він скомпілював, не інакше.

А якщо я зроблю запит ForTree:
Код: Виділити все id - з штатний распісаніе.ID
DEP_ID: IIf (IsNull (# 91; штатний распісаніе.ДЕПАРТ # 93;); ""; "b" # 91; штатний распісаніе.ДЕПАРТ # 93;)
OTD_ID: IIf (IsNull (# 91; штатний распісаніе.ОТДЕЛ # 93;); ""; "з" # 91; штатний распісаніе.ОТДЕЛ # 93;)
SEK_ID: IIf (IsNull (# 91; штатний распісаніе.СЕКТОР # 93;); ""; "d" # 91; штатний распісаніе.СЕКТОР # 93;)
DOLJ_ID: IIf (IsNull (# 91; штатний распісаніе.ДОЛЖНОСТЬ # 93;); ""; "e" # 91; штатний распісаніе.ДОЛЖНОСТЬ # 93;)
DEP_NAME: СПР_ДЕПАРТ.Name
OTD_NAME: СПР_ОТДЕЛ.Name
SEK_NAME: СПР_СЕКТОР.Name
DOLJ_NAME: СПР_ДОЛЖНОСТЬ.Name
А потім пройдуся по записах і додам гілки?
Код: Виділити все якщо DEP_ID <> Null, то
Parent_ID. = ""; Key. = DEP_ID; Name. = DEP_NAME;
TreeView.Add (Parent_ID. Key, Name);

якщо OTD_ID <> Null, то
Parent_ID. = DEP_ID; Key. = OTD_ID; Name. = OTD_NAME;
TreeView.Add (Parent_ID, child, Key, Name);

якщо SEK_ID <> Null, то
Parent_ID. = OTD_ID; Key. = SEK_ID; Name. = SEK_NAME;
TreeView.Add (Parent_ID, child, Key, Name);
'Поле ПОСАДУ обов'язкове. Пусто бути не може
Parent_ID. = SEK_ID; Key. = DOLJ_ID; Name. = DOLJ_NAME;
TreeView.Add (Parent_ID, child, Key, Name);
інакше 'у посади батько - відділ
Parent_ID. = OTD_ID; Key. = DOLJ_ID; Name. = DOLJ_NAME;
TreeView.Add (Parent_ID, child, Key, Name);
Як це укласти в синтаксис VB?

Як пройтися по записах, враховуючи цей код і синтаксис VB?

А потім, уже при сформованому дереві, при виділенні листа дерева, тобто посади, мені потрібно відобразити ПІБ працівника з Особистої картки (ЛК). ЛК буде пов'язана із запитом ForTree по СТАВКАШТ.ЛК і ForTree.ID.
і зв'яжу штатний распісаніе.ID і ForTree.ID. Так я хочу відобразити ПІБ з ЛК і характеристики посади зі штатного розпису при виділеному аркуші дерева.

Таке можливо? Допоможіть з логікою!
А тепер те, заради чого це все затівається:
створити найбільш зручний інтерфейс для додавання / видалення / зміни всіх вузлів дерева. Естествеено із записом в таблицю штатного розкладу. 4 день б'юся. HELP!

ось що у мене вийшло після довгих пошуків в інтернеті!
Добрі люди допомагали на форумах!

Схожі статті