构建乘积数组
正则表达式匹配
构建乘积数组
问题
给定一个数组A[0,1,…,n-1],请构建一个数组B[0,1,…,n-1],其中B中的元素B[i]=A[0]A[1]…A[i-1]A[i+1]…A[n-1]。不能使用除法。
分析: 思路1:
其实对B的每一个元素,都可以以下标i,把整个乘积分为前后两个部分:B[i]=A[i-1]及之前的累计乘积* A[i]之后到A[n-1]的乘积(以A
[i]为分界点),分别对前后去求,然后更新。
实现细节:以对角线A[i]为界,分为左下部分与右上两部分。可以先做左下部分,从上往下,做一个循环,B中前半部分的当前的每一个元素,是A中对应的一个值和前一个B的值相乘得到。然后再对右上部分做一个循环,从下往上,开一个temp 记录右侧已有的乘积,再把右侧的值乘以原来左侧的值,更新B[i].
思路2:能否做一个循环,当计算B[i]再循环时,碰到A[i],就用1来作为值去乘. 虽然,相对1,计算量重复了一些.但bingo!
思路1代码:
# -*- coding:utf-8 -*-
class Solution:
def multiply(self,A):
if not A:
return []
B=[1]*len(A)
#先做左下部分,从上往下累乘左下半
for i in range(1,len(A)):
B[i]=B[i-1]*A[i-1]
#再做右上部分,这时可以从右下往上乘积。注意此时需要开辟一个temp来存储右侧A的累乘积了
temp=1
for i in range(len(A)-2,-1,-1):
temp=temp*A[i+1]
B[i]=B[i]*temp #左侧的*右侧的,更新了 B[i]
return B
思路2代码:
##**思路2:能否做一个循环,当计算B[i]再循环时,碰到A[i],就用1来作为值去乘.**
def multiply_two(A):
if not A:
return []
B=[1]*len(A)
for i in range(len(B)):
temp=1
for j in range(len(A)):
if i==j:
temp=temp*1
else:
temp=temp*A[j]
B[i]=temp
return B
A_two=[1,2,3,4,5]
BB_two=multiply_two(A)
print(BB_two)
正则表达式匹配
问题
请实现一个函数用来匹配包括'.'和'*'的正则表达式。模式中的字符'.'表示任意一个字符,而'*'表示它前面的字符可以出现任意次(包含0次)。 在本题中,匹配是指字符串的所有字符匹配整个模式。例如,字符串"aaa"与模式"a.a"和"ab*ac*a"匹配,但是与"aa.a"和"ab*a"均不匹配
思路
这道题相对比较复杂。重点是要思路清晰,注意用到递归去判断…要注意讨论各种各样的情况,导致无法通过所有用例。
对初始输入的判断:
如果s和pattern都为空,则True;如果s不空,而pattern为空,则直接False.
然后来读取pattern中的每个字符:
- 如果当前pattern字符的后面不是* ,则说明只可匹配1个
- 如果当前pattern字符是.的话,可匹配1个任意字符
- 如果不是点,则只能匹配给出的字符,若不匹配则直接返回
- 完成后两者均往后+1,继续判断
- 如果当前pattern字符的后面是* ,说明当前pattern字符可匹配0-任意多个。
- 如果当前pattern字符与串的字符不一致,而且pattern当前字符不是点,则当作是 * 的未匹配的情况,pattern往后+2而字符串不变(如aaa与ab*ac*中b*的情况)(此处自己改动后还是好理解多了)
- 否则其他情况:
- 要么共匹配0个,pattern往后+2,字符串不变
- 要么共匹配1个,字符串往后+1, pattern 往后+2
- 要么先匹配1个,留待继续匹配,此时字符串+1, pattern不变
- 然后继续匹配后面的是否match
# -*- coding:utf-8 -*- class Solution: # s, pattern都是字符串 def match(self,s,pattern): #如果s和pattern都为空,则返回true if len(s)==0 and len(pattern)==0: return True #如果s不为空,pattern为空,则返回false elif len(s)!=0 and len(pattern)==0: return False #如果s为空,而pattern不为空,则需要判断 elif len(s)==0 and len(pattern)!=0: #pattern的第二个字符为*,则pattern后移两位继续比较 if len(pattern)>1 and pattern[1]=="*": ###### ##注意用递归 ######### return self.match(s,pattern[2:]) else: return False else: #s 与pattern 都不为空的情况 #pattern 的第二个字符为*的情况 if len(pattern)>1 and pattern[1]=="*": # s与pattern的第一个元素不同,则s不变,pattern后移两位,相当于pattern前两位看成空 if s[0]!=pattern[0] and pattern[0]!=".": return self.match(s,pattern[2:]) else: #如果s[0]与pattern[0]相同,且pattern[1]为*,这时有三种情况 #pattern后移2个,s不变;相当于也把pattern前两位看成空,匹配后面的 #pattern 后移两位,s后移1位,相当于pattern的前两位与s[0]匹配 ####此注意与s多位情况 #pattern不变,s后移1个;相当于pattern前两位与s中多位进行 匹配,因为*可以匹配多位 return self.match(s,pattern[2:]) or self.match(s[1:],pattern[2:]) or self.match(s[1:],pattern) #pattern第二个字符不为*的情况 else: if s[0]==pattern[0] or pattern[0]==".": return self.match(s[1:],pattern[1:]) else: return False