📌  相关文章
📜  从词法上讲,Kth从原点到达指定坐标的最小方式

📅  最后修改于: 2021-05-04 07:49:53             🧑  作者: Mango

给定2D平面上的坐标(x,y) 。我们必须从原点即(0,0)的当前位置到达(x,y)。在每个步骤中,我们都可以在平面上垂直或水平移动。在每个步骤中水平移动时,我们都写为“ H”,在每个步骤中垂直移动时,我们都写为“ V”。因此,可能有许多包含’H’和’V’的字符串,它们表示从(0,0)到(x,y)的路径。任务是在所有可能的字符串找到按字典顺序排列的第K个最小字符串。

例子:

先决条件:从起点到达终点的方法

方法:想法是使用递归来解决问题。从原点到达(x,y)的方式为x + y C x
现在观察,从(1,0)到达(x,y)的方式将是(x + y – 1,x – 1),因为我们已经在水平方向上进行了一步,因此从中减去1 X。同样,从(0,1)到达(x,y)的方式将是(x + y – 1,y – 1),因为我们已经在垂直方向上迈出了一步,所以从y减去1 。由于“ H”在字典上小于“ V”,因此在所有字符串中,起始字符串的开头将包含“ H”,即,初始运动将为“水平”。
因此,如果K <= x + y – 1 C x – 1 ,我们将“ H”作为第一步,否则将“ V”作为第一步,并求解从(1 ,0)将为K = K – x + y – 1 C x – 1

以下是此方法的实现:

C++
// CPP Program to find Lexicographically Kth
// smallest way to reach given coordinate from origin
#include 
using namespace std;
  
// Return (a+b)!/a!b!
int factorial(int a, int b)
{
    int res = 1;
  
    // finding (a+b)!
    for (int i = 1; i <= (a + b); i++)
        res = res * i;
  
    // finding (a+b)!/a!
    for (int i = 1; i <= a; i++)
        res = res / i;
  
    // finding (a+b)!/b!
    for (int i = 1; i <= b; i++)
        res = res / i;
  
    return res;
}
  
// Return the Kth smallest way to reach given coordinate from origin
void Ksmallest(int x, int y, int k)
{
    // if at origin
    if (x == 0 && y == 0)
        return;
  
    // if on y-axis
    else if (x == 0) {
        // decrement y.
        y--;
  
        // Move vertical
        cout << "V";
  
        // recursive call to take next step.
        Ksmallest(x, y, k);
    }
  
    // If on x-axis
    else if (y == 0) {
        // decrement x.
        x--;
  
        // Move horizontal.
        cout << "H";
  
        // recursive call to take next step.
        Ksmallest(x, y, k);
    }
    else {
        // If x + y C x is greater than K
        if (factorial(x - 1, y) > k) {
            // Move Horizontal
            cout << "H";
  
            // recursive call to take next step.
            Ksmallest(x - 1, y, k);
        }
        else {
            // Move vertical
            cout << "V";
  
            // recursive call to take next step.
            Ksmallest(x, y - 1, k - factorial(x - 1, y));
        }
    }
}
  
// Driven Program
int main()
{
    int x = 2, y = 2, k = 2;
  
    Ksmallest(x, y, k);
  
    return 0;
}


Java
// Java Program to find 
// Lexicographically Kth 
// smallest way to reach
// given coordinate from origin
import java.io.*;
  
class GFG 
{
  
// Return (a+b)!/a!b!
static int factorial(int a, 
                     int b)
{
    int res = 1;
  
    // finding (a+b)!
    for (int i = 1; 
             i <= (a + b); i++)
        res = res * i;
  
    // finding (a+b)!/a!
    for (int i = 1; i <= a; i++)
        res = res / i;
  
    // finding (a+b)!/b!
    for (int i = 1; i <= b; i++)
        res = res / i;
  
    return res;
}
  
// Return the Kth smallest 
// way to reach given 
// coordinate from origin
static void Ksmallest(int x, 
                      int y, int k)
{
    // if at origin
    if (x == 0 && y == 0)
        return;
  
    // if on y-axis
    else if (x == 0)
    {
        // decrement y.
        y--;
  
        // Move vertical
        System.out.print("V");
  
        // recursive call to
        // take next step.
        Ksmallest(x, y, k);
    }
  
    // If on x-axis
    else if (y == 0) 
    {
        // decrement x.
        x--;
  
        // Move horizontal.
        System.out.print("H");
  
        // recursive call to
        // take next step.
        Ksmallest(x, y, k);
    }
    else
    {
        // If x + y C x is
        // greater than K
        if (factorial(x - 1, y) > k)
        {
            // Move Horizontal
            System.out.print( "H");
  
            // recursive call to
            // take next step.
            Ksmallest(x - 1, y, k);
        }
        else 
        {
            // Move vertical
            System.out.print("V");
  
            // recursive call to
            // take next step.
            Ksmallest(x, y - 1, k - 
            factorial(x - 1, y));
        }
    }
}
  
// Driver Code
public static void main (String[] args)
{
    int x = 2, y = 2, k = 2;
  
    Ksmallest(x, y, k);
}
}
  
// This code is contributed 
// by anuj_67.


Python3
# Python3 Program to find Lexicographically Kth 
# smallest way to reach given coordinate from origin 
  
# Return (a+b)!/a!b! 
def factorial(a, b): 
  
    res = 1
  
    # finding (a+b)! 
    for i in range(1, a + b + 1): 
        res = res * i 
  
    # finding (a+b)!/a! 
    for i in range(1, a + 1): 
        res = res // i 
  
    # finding (a+b)!/b! 
    for i in range(1, b + 1): 
        res = res // i 
  
    return res 
  
# Return the Kth smallest way to reach
# given coordinate from origin 
def Ksmallest(x, y, k): 
  
    # if at origin 
    if x == 0 and y == 0: 
        return
  
    # if on y-axis 
    elif x == 0:
        # decrement y. 
        y -= 1
  
        # Move vertical 
        print("V", end = "") 
  
        # recursive call to take next step. 
        Ksmallest(x, y, k) 
      
    # If on x-axis 
    elif y == 0:
          
        # decrement x. 
        x -= 1
  
        # Move horizontal. 
        print("H", end = "") 
  
        # recursive call to take next step. 
        Ksmallest(x, y, k) 
      
    else:
          
        # If x + y C x is greater than K 
        if factorial(x - 1, y) > k: 
              
            # Move Horizontal 
            print("H", end = "")
  
            # recursive call to take next step. 
            Ksmallest(x - 1, y, k) 
          
        else:
              
            # Move vertical 
            print("V", end = "") 
  
            # recursive call to take next step. 
            Ksmallest(x, y - 1, k - factorial(x - 1, y)) 
          
# Driver Code
if __name__ == "__main__": 
  
    x, y, k = 2, 2, 2
    Ksmallest(x, y, k) 
  
# This code is contributed by Rituraj Jain


C#
// C# Program to find 
// Lexicographically Kth 
// smallest way to reach
// given coordinate from origin 
using System;
  
class GFG 
{
  
// Return (a+b)!/a!b!
static int factorial(int a, 
                    int b)
{
    int res = 1;
  
    // finding (a+b)!
    for (int i = 1; 
            i <= (a + b); i++)
        res = res * i;
  
    // finding (a+b)!/a!
    for (int i = 1; i <= a; i++)
        res = res / i;
  
    // finding (a+b)!/b!
    for (int i = 1; i <= b; i++)
        res = res / i;
  
    return res;
}
  
// Return the Kth smallest 
// way to reach given 
// coordinate from origin
static void Ksmallest(int x, 
                    int y, int k)
{
    // if at origin
    if (x == 0 && y == 0)
        return;
  
    // if on y-axis
    else if (x == 0)
    {
        // decrement y.
        y--;
  
        // Move vertical
        Console.Write("V");
  
        // recursive call to
        // take next step.
        Ksmallest(x, y, k);
    }
  
    // If on x-axis
    else if (y == 0) 
    {
        // decrement x.
        x--;
  
        // Move horizontal.
        Console.Write("H");
  
        // recursive call to
        // take next step.
        Ksmallest(x, y, k);
    }
    else
    {
        // If x + y C x is
        // greater than K
        if (factorial(x - 1, y) > k)
        {
            // Move Horizontal
            Console.Write( "H");
  
            // recursive call to
            // take next step.
            Ksmallest(x - 1, y, k);
        }
        else
        {
            // Move vertical
            Console.Write("V");
  
            // recursive call to
            // take next step.
            Ksmallest(x, y - 1, k - 
            factorial(x - 1, y));
        }
    }
}
  
// Driver Code
public static void Main (String[] args)
{
    int x = 2, y = 2, k = 2;
  
    Ksmallest(x, y, k);
}
}
  
// This code is contributed by 29AjayKumar


PHP
 $k)
        {
            // Move Horizontal
            echo("H");
  
            // recursive call to
            // take next step.
            Ksmallest($x - 1, $y, $k);
        }
        else
        {
            // Move vertical
            echo("V");
  
            // recursive call to
            // take next step.
            Ksmallest($x, $y - 1, $k - 
            factorial($x - 1, $y));
        }
    }
}
  
// Driver Code
$x = 2; $y = 2;$k = 2;
  
Ksmallest($x, $y, $k);
  
// This code is contributed 
// by Code_Mech.
?>


输出

HVVH