USACO23JAN Find and Replace S (Luogu P9013) Solution
The content below was generated entirely by machine translation. Please verify its accuracy. If anything is unclear, consult the Chinese source version.
The reading experience is better on the blog
Analysis
The statement is very concise: given a series of character replacements, find the minimum number of steps required to turn string into string .
After receiving the problem, we can first analyze the samples.
From the sample , we can see that it is impossible to replace one character with two characters at the same time (), because this creates a conflict.
Then, can the number of positions where (after deduplicating the strings, so cases such as do not exist) directly be used as the answer? The final sample shows that this is not the case.
Handling Cycles
Because the part in the final sample is the same, let us directly consider the transformation . If we directly perform the operation , we obtain a string . At this point, the same problem as before appears: it cannot be transformed into . Performing is analogous.
The solution is to first perform and then process ( is any other character).
Can all mutually dependent cases be solved in this way? Let us consider a larger sample, . It is clearer to represent it as a graph (create an edge and remove duplicate edges and self-loops):
graph LR
A --> B
B --> C
C --> D
D --> A
This is a cycle. No matter which transformation we perform first, we will need to perform a transformation afterward, because wants to become something else. At this point, the earlier will also be changed to .
However, the problem can be solved if we can “turn the cycle into a chain.” For example, we can first perform , turning the chain into:
graph LR
x --> B
B --> C
C --> D
D --> A
Now there is a place where, after executing , we do not need to execute : . (After executing it, also satisfies this condition, so we can convert the entire string to the target by following the chain backward.)
These two examples show that, in general, one operation can turn a cycle into a chain, or reduce the length of a chain (the number of edges) by 1.
So is the answer the number of cycles plus the length of the chains?
Two Special Cases
1
First, turning a cycle into a chain requires a character that does not appear in the cycle. If the cycle contains every character in the character set, we cannot handle it.
Suppose our character set contains only the four characters . When processing the following example, we encounter a problem:
graph LR
A --> B
B --> C
C --> D
D --> A
No matter which character we change into first, that character will undergo at least one more transformation afterward, preventing from being transformed into the target character .
Of course, an unprocessable case does not necessarily require the entire graph to contain only one cycle. It is enough that:
- Every node is in a cycle.
- Every character in the character set is used.
For example, the following case with two cycles is also impossible (the character set is ):
graph LR
A --> B
B --> A
C --> D
D --> C
2
Consider the input :
graph LR
A --> B
B --> C
C --> D
D --> A
E --> B
F --> E
We can turn the cycle into a chain and reduce the chain length by 1 in a single operation. Observe that both and want to be transformed into . From the perspective of character transformations, and have the same final result and number of steps. However, when executing , the second method also transforms a character in the cycle into a character outside the cycle, turning the cycle into a chain.
The prerequisite for doing this is that multiple characters outside the cycle want to become one character inside the cycle. More precisely, some node in the cycle must have in-degree at least 2.
At this point, all cases have essentially been analyzed, and we can summarize them as follows (the conditions in parentheses are the actual checks):
- If one character wants to be transformed into multiple characters, there is no solution. (Every node has out-degree at most 1.)
- If all nodes (all possible characters) are in cycles, there is no solution. (Every character has in-degree 1.)
- Answer = number of edges + number of absolute cycles (every node in the cycle has both in-degree and out-degree equal to 1).
The check for the second point can be explained slightly. We do not choose to use out-degree because of the case where a cycle is connected to a tree; see the figure above.
Code Implementation
When implementing this, pay attention to the cycle-finding part; the other parts are relatively simple.
We know that Tarjan’s algorithm can detect cycles. However, this problem can use a “simplified version” of Tarjan that does not record discovery timestamps. During DFS, we push every visited node from the back of a deque.
If DFS starts from a node on a cycle, it must eventually visit a node equal to the front of the deque. At this point, popping all nodes between the front and back gives all nodes in the cycle.
If we find that a node was visited previously but is not at the front, we can determine that the nodes in the deque are not an “absolute cycle,” because a tree is connected to it (as in the figure above, this happens if the search starts from node F).
1 |
|






![[Stanford CS144] Lab 4 Record](/img/CS144/tcp%E7%8A%B6%E6%80%81%E6%B5%81%E8%BD%AC%E5%9B%BE.jpg)