<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="ru">
		<id>http://neerc.ifmo.ru/wiki/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=178.178.2.220&amp;*</id>
		<title>Викиконспекты - Вклад участника [ru]</title>
		<link rel="self" type="application/atom+xml" href="http://neerc.ifmo.ru/wiki/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=178.178.2.220&amp;*"/>
		<link rel="alternate" type="text/html" href="http://neerc.ifmo.ru/wiki/index.php?title=%D0%A1%D0%BB%D1%83%D0%B6%D0%B5%D0%B1%D0%BD%D0%B0%D1%8F:%D0%92%D0%BA%D0%BB%D0%B0%D0%B4/178.178.2.220"/>
		<updated>2026-06-11T14:08:38Z</updated>
		<subtitle>Вклад участника</subtitle>
		<generator>MediaWiki 1.30.0</generator>

	<entry>
		<id>http://neerc.ifmo.ru/wiki/index.php?title=%D0%9C%D0%B8%D0%BD%D0%B8%D0%BC%D0%B8%D0%B7%D0%B0%D1%86%D0%B8%D1%8F_%D0%94%D0%9A%D0%90,_%D0%B0%D0%BB%D0%B3%D0%BE%D1%80%D0%B8%D1%82%D0%BC_%D0%A5%D0%BE%D0%BF%D0%BA%D1%80%D0%BE%D1%84%D1%82%D0%B0_(%D1%81%D0%BB%D0%BE%D0%B6%D0%BD%D0%BE%D1%81%D1%82%D1%8C_O(n_log_n))&amp;diff=18079</id>
		<title>Минимизация ДКА, алгоритм Хопкрофта (сложность O(n log n))</title>
		<link rel="alternate" type="text/html" href="http://neerc.ifmo.ru/wiki/index.php?title=%D0%9C%D0%B8%D0%BD%D0%B8%D0%BC%D0%B8%D0%B7%D0%B0%D1%86%D0%B8%D1%8F_%D0%94%D0%9A%D0%90,_%D0%B0%D0%BB%D0%B3%D0%BE%D1%80%D0%B8%D1%82%D0%BC_%D0%A5%D0%BE%D0%BF%D0%BA%D1%80%D0%BE%D1%84%D1%82%D0%B0_(%D1%81%D0%BB%D0%BE%D0%B6%D0%BD%D0%BE%D1%81%D1%82%D1%8C_O(n_log_n))&amp;diff=18079"/>
				<updated>2012-02-13T22:02:57Z</updated>
		
		<summary type="html">&lt;p&gt;178.178.2.220: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;= Постановка задачи =&lt;br /&gt;
Пусть дан автомат, распознающий определенный язык. Требуется найти [[ Эквивалентность_состояний_ДКА | эквивалентный автомат]] с наименьшим количеством состояний.&lt;br /&gt;
&lt;br /&gt;
= Алгоритм Хопкрофта=&lt;br /&gt;
Если в ДКА существуют два [[ Эквивалентность_состояний_ДКА | эквивалентных состояния]], то при их объединении мы получим [[ Эквивалентность_состояний_ДКА | эквивалентный ДКА]], так как распознаваемый язык не изменится. Основная идея алгоритма состоит в разбиении множества состояний на классы эквивалентности, полученные классы и будут состояниями минимизированного ДКА.  &lt;br /&gt;
&lt;br /&gt;
Итеративно строим разбиение множества состояний следующим образом.&lt;br /&gt;
# Первоначальное разбиение множества состояний {{---}} класс допускающих состояний и класс недопускающих состояний.&lt;br /&gt;
# Меньший из них помещается в очередь.&lt;br /&gt;
# Из очереди извлекается класс, далее именуемый как сплиттер.&lt;br /&gt;
# Перебираются все символы из алфавита &amp;lt;tex&amp;gt;\Sigma&amp;lt;/tex&amp;gt;, где &amp;lt;tex&amp;gt;c&amp;lt;/tex&amp;gt; {{---}} текущий символ.&lt;br /&gt;
# Все классы текущего разбиения разбиваются на 2 подкласса (один из которых может быть пустым). Первый состоит из состояний, которые по символу &amp;lt;tex&amp;gt;c&amp;lt;/tex&amp;gt; переходят в сплиттер, а второй из всех оставшихся. &lt;br /&gt;
# Те классы, которые разбились на два непустых подкласса, заменяются этими подклассами в разбиении, а также меньший из двух подклассов добавляется в очередь.&lt;br /&gt;
# Пока очередь не пуста, алгоритм выполняет п.3 – п.6.&lt;br /&gt;
&lt;br /&gt;
===Псевдокод===&lt;br /&gt;
&amp;lt;tex&amp;gt;Q&amp;lt;/tex&amp;gt; {{---}} множество состояний ДКА.&lt;br /&gt;
&amp;lt;tex&amp;gt;F&amp;lt;/tex&amp;gt; {{---}} множество терминальных состояний.&lt;br /&gt;
&amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt; {{---}} очередь.&lt;br /&gt;
&amp;lt;tex&amp;gt;P&amp;lt;/tex&amp;gt; {{---}} разбиение множества состояний ДКА.&lt;br /&gt;
&amp;lt;tex&amp;gt;R&amp;lt;/tex&amp;gt; {{---}} класс состояний ДКА.&lt;br /&gt;
  if &amp;lt;tex&amp;gt; |F| \le |Q \setminus F|&amp;lt;/tex&amp;gt;&lt;br /&gt;
      &amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt;.push(&amp;lt;tex&amp;gt;F&amp;lt;/tex&amp;gt;)&lt;br /&gt;
    else&lt;br /&gt;
      &amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt;.push(&amp;lt;tex&amp;gt;Q \setminus F&amp;lt;/tex&amp;gt;)&lt;br /&gt;
  &amp;lt;tex&amp;gt;P \leftarrow \{ F, Q \setminus F \}&amp;lt;/tex&amp;gt;&lt;br /&gt;
  while not &amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt;.isEmpty() &lt;br /&gt;
    &amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt;.pop(&amp;lt;tex&amp;gt;S&amp;lt;/tex&amp;gt;)&lt;br /&gt;
    for all &amp;lt;tex&amp;gt;a \in \Sigma&amp;lt;/tex&amp;gt;&lt;br /&gt;
      for all &amp;lt;tex&amp;gt;R&amp;lt;/tex&amp;gt; in &amp;lt;tex&amp;gt;P&amp;lt;/tex&amp;gt; &lt;br /&gt;
        &amp;lt;tex&amp;gt;R_1 = R \cap \delta^{-1} (S, a) &amp;lt;/tex&amp;gt;&lt;br /&gt;
        &amp;lt;tex&amp;gt;R_2 = R \setminus R_1&amp;lt;/tex&amp;gt;&lt;br /&gt;
        if &amp;lt;tex&amp;gt; |R_1| \ne 0&amp;lt;/tex&amp;gt; and &amp;lt;tex&amp;gt;|R_2| \ne 0&amp;lt;/tex&amp;gt;&lt;br /&gt;
          replace &amp;lt;tex&amp;gt;R&amp;lt;/tex&amp;gt; in &amp;lt;tex&amp;gt;P&amp;lt;/tex&amp;gt; with &amp;lt;tex&amp;gt;R_1&amp;lt;/tex&amp;gt; and &amp;lt;tex&amp;gt;R_2&amp;lt;/tex&amp;gt;&lt;br /&gt;
          if &amp;lt;tex&amp;gt;R&amp;lt;/tex&amp;gt; in &amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt;&lt;br /&gt;
              replace &amp;lt;tex&amp;gt;R&amp;lt;/tex&amp;gt; in &amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt; with &amp;lt;tex&amp;gt;R_1&amp;lt;/tex&amp;gt; and &amp;lt;tex&amp;gt;R_2&amp;lt;/tex&amp;gt;&lt;br /&gt;
            else&lt;br /&gt;
              if &amp;lt;tex&amp;gt; |R_1| \le |R_2|&amp;lt;/tex&amp;gt;&lt;br /&gt;
                  &amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt;.push(&amp;lt;tex&amp;gt;R_1&amp;lt;/tex&amp;gt;)&lt;br /&gt;
                else&lt;br /&gt;
                  &amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt;.push(&amp;lt;tex&amp;gt;R_2&amp;lt;/tex&amp;gt;)&lt;br /&gt;
=Корректность алгоритма=&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=Время работы алгоритма=&lt;br /&gt;
Благодаря системе добавления классов состояний в очередь, каждое ребро будет рассмотрено не более чем &amp;lt;tex&amp;gt;\log{n}&amp;lt;/tex&amp;gt; раз. А так как ребер у нас порядка &amp;lt;tex&amp;gt; |\Sigma| * n &amp;lt;/tex&amp;gt; то получаем &amp;lt;tex&amp;gt; O(n\log{n})&amp;lt;/tex&amp;gt;&lt;br /&gt;
= Литература =&lt;br /&gt;
* ''Хопкрофт Д., Мотвани Р., Ульман Д.'' Введение в теорию автоматов, языков и вычислений, 2-е изд. : Пер. с англ. — М.: Издательский дом «Вильямс», 2002. — С. 177 — ISBN 5-8459-0261-4 (рус.)&lt;br /&gt;
* ''J. E. Hopcroft.'' An n log n algorithm for minimizing states in a finite automaton. Technical Report CS-71-190, Stanford University, January 1971.&lt;br /&gt;
&lt;br /&gt;
[[Категория: Теория формальных языков]]&lt;br /&gt;
[[Категория: Автоматы и регулярные языки]]&lt;/div&gt;</summary>
		<author><name>178.178.2.220</name></author>	</entry>

	<entry>
		<id>http://neerc.ifmo.ru/wiki/index.php?title=%D0%9C%D0%B8%D0%BD%D0%B8%D0%BC%D0%B8%D0%B7%D0%B0%D1%86%D0%B8%D1%8F_%D0%94%D0%9A%D0%90,_%D0%B0%D0%BB%D0%B3%D0%BE%D1%80%D0%B8%D1%82%D0%BC_%D0%A5%D0%BE%D0%BF%D0%BA%D1%80%D0%BE%D1%84%D1%82%D0%B0_(%D1%81%D0%BB%D0%BE%D0%B6%D0%BD%D0%BE%D1%81%D1%82%D1%8C_O(n_log_n))&amp;diff=18078</id>
		<title>Минимизация ДКА, алгоритм Хопкрофта (сложность O(n log n))</title>
		<link rel="alternate" type="text/html" href="http://neerc.ifmo.ru/wiki/index.php?title=%D0%9C%D0%B8%D0%BD%D0%B8%D0%BC%D0%B8%D0%B7%D0%B0%D1%86%D0%B8%D1%8F_%D0%94%D0%9A%D0%90,_%D0%B0%D0%BB%D0%B3%D0%BE%D1%80%D0%B8%D1%82%D0%BC_%D0%A5%D0%BE%D0%BF%D0%BA%D1%80%D0%BE%D1%84%D1%82%D0%B0_(%D1%81%D0%BB%D0%BE%D0%B6%D0%BD%D0%BE%D1%81%D1%82%D1%8C_O(n_log_n))&amp;diff=18078"/>
				<updated>2012-02-13T20:57:21Z</updated>
		
		<summary type="html">&lt;p&gt;178.178.2.220: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;= Постановка задачи =&lt;br /&gt;
Пусть дан автомат, распознающий определенный язык. Требуется найти [[ Эквивалентность_состояний_ДКА | эквивалентный автомат]] с наименьшим количеством состояний.&lt;br /&gt;
&lt;br /&gt;
= Минимизация ДКА =&lt;br /&gt;
Понятие [[ Эквивалентность_состояний_ДКА | эквивалентности состояний]] позволяет объединить состояния в классы следующим образом.&lt;br /&gt;
# Все состояния в классе эквивалентны.&lt;br /&gt;
# Любые два состояния, выбранные из разных класов, неэквивалентны.&lt;br /&gt;
Таким образом, основная идея минимизации ДКА состоит в разбиении множества состояний на классы эквивалентности.&lt;br /&gt;
===Пример минимизации ДКА===&lt;br /&gt;
[[Изображение:Automaton1.png]][[Изображение:Automaton2.png]]&lt;br /&gt;
&lt;br /&gt;
Первый класс состоит из состояния &amp;lt;tex&amp;gt;A&amp;lt;/tex&amp;gt;, а второй из эквивалентных состояний &amp;lt;tex&amp;gt;B&amp;lt;/tex&amp;gt; и &amp;lt;tex&amp;gt;C&amp;lt;/tex&amp;gt;.&lt;br /&gt;
= Алгоритм =&lt;br /&gt;
Итеративно строим разбиение множества состояний следующим образом.&lt;br /&gt;
# Первоначальное разбиение множества состояний {{---}} класс допускающих состояний и класс недопускающих состояний.&lt;br /&gt;
# Меньший из них помещается в очередь.&lt;br /&gt;
# Из очереди извлекается класс, далее именуемый как сплиттер.&lt;br /&gt;
# Перебираются все символы из алфавита &amp;lt;tex&amp;gt;\Sigma&amp;lt;/tex&amp;gt;, где &amp;lt;tex&amp;gt;c&amp;lt;/tex&amp;gt; {{---}} текущий символ.&lt;br /&gt;
# Все классы текущего разбиения разбиваются на 2 подкласса (один из которых может быть пустым). Первый состоит из состояний, которые по символу &amp;lt;tex&amp;gt;c&amp;lt;/tex&amp;gt; переходят в сплиттер, а второй из всех оставшихся. &lt;br /&gt;
# Те классы, которые разбились на два непустых подкласса, заменяются этими подклассами в разбиении, а также меньший из двух подклассов добавляется в очередь.&lt;br /&gt;
# Пока очередь не пуста, алгоритм выполняет п.3 – п.6.&lt;br /&gt;
&lt;br /&gt;
===Псевдокод===&lt;br /&gt;
&amp;lt;tex&amp;gt;Q&amp;lt;/tex&amp;gt; {{---}} множество состояний ДКА.&lt;br /&gt;
&amp;lt;tex&amp;gt;F&amp;lt;/tex&amp;gt; {{---}} множество терминальных состояний.&lt;br /&gt;
&amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt; {{---}} очередь.&lt;br /&gt;
&amp;lt;tex&amp;gt;P&amp;lt;/tex&amp;gt; {{---}} разбиение множества состояний ДКА.&lt;br /&gt;
&amp;lt;tex&amp;gt;R&amp;lt;/tex&amp;gt; {{---}} класс состояний ДКА.&lt;br /&gt;
  if &amp;lt;tex&amp;gt; |F| \le |Q \setminus F|&amp;lt;/tex&amp;gt;&lt;br /&gt;
      &amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt;.push(&amp;lt;tex&amp;gt;F&amp;lt;/tex&amp;gt;)&lt;br /&gt;
    else&lt;br /&gt;
      &amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt;.push(&amp;lt;tex&amp;gt;Q \setminus F&amp;lt;/tex&amp;gt;)&lt;br /&gt;
  &amp;lt;tex&amp;gt;P \leftarrow \{ F, Q \setminus F \}&amp;lt;/tex&amp;gt;&lt;br /&gt;
  while not &amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt;.isEmpty() &lt;br /&gt;
    &amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt;.pop(&amp;lt;tex&amp;gt;S&amp;lt;/tex&amp;gt;)&lt;br /&gt;
    for all &amp;lt;tex&amp;gt;a \in \Sigma&amp;lt;/tex&amp;gt;&lt;br /&gt;
      for all &amp;lt;tex&amp;gt;R&amp;lt;/tex&amp;gt; in &amp;lt;tex&amp;gt;P&amp;lt;/tex&amp;gt; &lt;br /&gt;
        &amp;lt;tex&amp;gt;R_1 = R \cap \delta^{-1} (S, a) &amp;lt;/tex&amp;gt;&lt;br /&gt;
        &amp;lt;tex&amp;gt;R_2 = R \setminus R_1&amp;lt;/tex&amp;gt;&lt;br /&gt;
        if &amp;lt;tex&amp;gt; |R_1| \ne 0&amp;lt;/tex&amp;gt; and &amp;lt;tex&amp;gt;|R_2| \ne 0&amp;lt;/tex&amp;gt;&lt;br /&gt;
          replace &amp;lt;tex&amp;gt;R&amp;lt;/tex&amp;gt; in &amp;lt;tex&amp;gt;P&amp;lt;/tex&amp;gt; with &amp;lt;tex&amp;gt;R_1&amp;lt;/tex&amp;gt; and &amp;lt;tex&amp;gt;R_2&amp;lt;/tex&amp;gt;&lt;br /&gt;
          if &amp;lt;tex&amp;gt;R&amp;lt;/tex&amp;gt; in &amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt;&lt;br /&gt;
              replace &amp;lt;tex&amp;gt;R&amp;lt;/tex&amp;gt; in &amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt; with &amp;lt;tex&amp;gt;R_1&amp;lt;/tex&amp;gt; and &amp;lt;tex&amp;gt;R_2&amp;lt;/tex&amp;gt;&lt;br /&gt;
            else&lt;br /&gt;
              if &amp;lt;tex&amp;gt; |R_1| \le |R_2|&amp;lt;/tex&amp;gt;&lt;br /&gt;
                  &amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt;.push(&amp;lt;tex&amp;gt;R_1&amp;lt;/tex&amp;gt;)&lt;br /&gt;
                else&lt;br /&gt;
                  &amp;lt;tex&amp;gt;W&amp;lt;/tex&amp;gt;.push(&amp;lt;tex&amp;gt;R_2&amp;lt;/tex&amp;gt;)&lt;br /&gt;
&lt;br /&gt;
==Время работы алгоритма==&lt;br /&gt;
Благодаря системе добавления классов состояний в очередь, каждое ребро будет рассмотрено не более чем &amp;lt;tex&amp;gt;\log{n}&amp;lt;/tex&amp;gt; раз. А так как ребер у нас порядка &amp;lt;tex&amp;gt; |\Sigma| * n &amp;lt;/tex&amp;gt; то получаем &amp;lt;tex&amp;gt; O(n\log{n})&amp;lt;/tex&amp;gt;&lt;br /&gt;
= Литература =&lt;br /&gt;
* ''Хопкрофт Д., Мотвани Р., Ульман Д.'' Введение в теорию автоматов, языков и вычислений, 2-е изд. : Пер. с англ. — М.: Издательский дом «Вильямс», 2002. — С. 177 — ISBN 5-8459-0261-4 (рус.)&lt;br /&gt;
* ''J. E. Hopcroft.'' An n log n algorithm for minimizing states in a finite automaton. Technical Report CS-71-190, Stanford University, January 1971.&lt;br /&gt;
&lt;br /&gt;
[[Категория: Теория формальных языков]]&lt;br /&gt;
[[Категория: Автоматы и регулярные языки]]&lt;/div&gt;</summary>
		<author><name>178.178.2.220</name></author>	</entry>

	</feed>