简体   繁体   中英

Print a 'X' pattern of '*'

I'm trying to print this pattern in Python:

*     *
 *   * 
  * *
   *
  * *
 *   *
*     *

And came up with this code:

size = 7
inner_size = size - 3
space=0

for i in range(inner_size):
    print (' ' * space + '*' + ' ' * inner_size + '*')
    inner_size -=2
    space +=1
print "    *"

t_size=7
t_inner_size = 0
space=3
for i in range(inner_size):
    print (' ' * space + '*' + ' ' * inner_size + '*')
    inner_size +=2
    space -=1

But, it prints this :

*    *
 *  *
  **
   **
    *

How to print the required pattern? Is it possible to do this in one loop?

Here's one way to do it:

def pattern(size):
    for i in range(size):
        print("".join("*" if j == i or size - 1 - j == i else " "
                      for j in range(size)))

Details: i is the row index and j is the column index (both zero-based). The j == i condition generates a diagonal from upper-left to lower-right. The size - 1 - j == i condition generates a diagonal from upper-right to lower-left. Together, they produce the X shape.

When called with a size of 7:

pattern(7)

It prints:

*     *
 *   * 
  * *  
   *   
  * *  
 *   * 
*     *

Note that it works with both even and odd sizes. In the case of an even size, the resulting X will contain a 2x2 block of stars in the center.

Just another way of solving the problem:

for i in range(5):
      for j in range(5):
           if ((i==j) or j==(5-i-1)):
               print " *",
           else:
               print " ",
       print ""

~

I have used ideas from your existing code in the question and made a few tweaks to do it in a single loop with simple, crystal clear code:

def xprint(size):
    i,j = 0,size - 1

    while j >= 0 and i < size:

        initial_spaces = ' '*min(i,j)
        middle_spaces = ' '*(abs(i - j) - 1)
        final_spaces = ' '*(size - 1 - max(i,j))

        if j == i:
            print initial_spaces + '*' + final_spaces
        else:
            print initial_spaces + '*' + middle_spaces + '*' + final_spaces

        i += 1
        j -= 1

xprint(7) 

It prints out:

*     *
 *   * 
  * *  
   *   
  * *  
 *   * 
*     *

A linear-time straightforward way of doing it.

You asked if it can be done with a ' single loop ' . So there ya go:

n = 3
for i in range(-n, n + 1):
    print('{}*{}{}'.format(
        (n + 1 - abs(i)) * ' ',
        (2 * abs(i) - 1) * ' ',
        '' if i == 0 else '*'))

Explanation:

For any given line, we need 2 sets of spaces. Spaces before the first * , and spaces after the first * . This we are formatting our string as follows: {}*{}

Now we add an extra placeholder, because every line has 2x '*', except for the middle line. We're counting in a fashion similar to -3 -2 -1 0 1 2 3 , there middle line has index 0 . Thus now our string format has become {}*{}{} .

Now, space before the first * need n + 1 - abs(i) no. of spaces.
and spaces after the first * need n + 1 - abs(i) no of spaces.

Output (n=3):

 *     *
  *   *
   * *
    *
   * *
  *   *
 *     *

Output (n=5):

 *         *
  *       *
   *     *
    *   *
     * *
      *
     * *
    *   *
   *     *
  *       *
 *         *

Although people are using the entire pattern size as input, I think it's more intuitive to use the recurring size as input. So just change the value of n as desired.

PS: This is not the most elegant, nor is it the most legible solution. But it works in a single loop.

You can also do it like this:

pattern_size = 7
for t in range(pattern_size):
    pattern = list(" " * pattern_size)
    pattern[t] = "*"
    pattern[-(t+1)] = "*"
    print("".join(pattern))

Output:

*     *
 *   * 
  * *  
   *   
  * *  
 *   * 
*     *

Another code for the above pattern

i = 0
j = 6
for row in range(7):
    for column in range(7):
        if(column == i or column == j):
            print("*",end="")
        else:
            print(" ",end="")
    print("\n")
    i += 1
    j -= 1

Results in:

*     *

 *   * 

  * *  

   *   

  * *  

 *   * 

*     *

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM