D5-AcWing-8002816801803+复习785-799

Posted 程序员超时空

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了D5-AcWing-8002816801803+复习785-799相关的知识,希望对你有一定的参考价值。

我太菜了啊啊 啊啊啊啊啊!昨天上课,居然都没有学习!!!!!!!垃圾
今天赶快补啊啊 !

800

这是一道双指针,自己写的时候想到用暴力+单调性,但是没领会到如何用单调性,看了y总的视频。
发现单调性就是:i增大,j会减小,j代表使A【i】+B【j】》=x的最左边的数。
这样上面最多走m,下面最多走n,一共是m+n

n,m,x = map(int,input().split())

A = list(map(int,input().split()))
B = list(map(int,input().split()))

j=m-1
for i in range(n):
    while A[i]+B[j]>x:
        j -= 1
    if A[i]+B[j]==x:
        break
print(i,j)    

2816

感觉很简单啊,不知道y总在讲啥。。。

n,m = map(int,input().split())
A = list(map(int,input().split()))
B = list(map(int,input().split()))

i,j = 0,0
while i!=n and j!=m:
    if A[i]==B[j]:
        i +=1
        j +=1
    else:
        j +=1
if i==n:
    print('Yes')
else:
    print('No')

801

这道题考察的是位运算。
位运算一共有两种:
1、二进制表示中,第k位是多少
n>>k&1
2、lowbit——返回x的最后一位1(从左向右)
这个也可以用来看一共有几个1,就是这题
x&-x
这里的-x是补码+1【反正这么&了就可以返回最后一位负数】

n = int(input())
nums = list(map(int,input().split()))

def lowbit(x):
    return x&-x
for i in range(n):
    res = 0
    while nums[i]:
        nums[i] -= lowbit(nums[i])
        res += 1
    print(res,end=' ')
    i += 1

802

参考知乎大佬的区间和(离散化)。
10e9太大了,这里映射到10e5
具体区间化的操作就是:
1、找到所有需要区间化的坐标
2、去重、排序
3、写使两个区间对应起来的find(x)函数,用二分,查找alls【mid】==x的数,也就是,alls里等于x的数的相对位置,就是他在离散化后的相对位置,也是这里的返回值。不过因为要用区间和,所以从1开始。
4、查找坐标,在新的区间上进行操作。

n,m = map(int,input().split())
# x用100000,l和r用200000
a,s = [0]*300010,[0]*300010
# alls里面装所有需要离散化的坐标
alls,add,query=[],[],[]

for _ in range(n):
    x,c =map(int,input().split())
    # 这个是一组一起输入,不然x离散化后找不到对应的c了
    add.append((x,c))
    alls.append(x)
for _ in range(m):
    l,r = map(int,input().split())
    query.append((l,r))
    alls.append(l)
    alls.append(r)
    
# 去重+排序
alls = list(set(alls))
alls.sort()

# 找到离散化后的坐标
def find(x):
    l,r = 0,len(alls)-1
    while l<r:
        mid = l+r>>1
        if alls[mid]>=x:
            r = mid
        else:
            l = mid+1
        # 因为求区间和,所以加1,使坐标从1开始。
    return l+1
# 插入所有数   
for x,c in add:
    index = find(x)
    a[index] += c
    
# 处理前缀和
for i in range(1,300010):
    s[i] = s[i-1]+a[i]

for l,r in query:
    print(s[find(r)]-s[find(l)-1])

803区间合并

这题还是看的知乎大佬的。
区间合并主要的步骤是:
1、排序
在python里用
sorted(x,key=lambda x:(x[0],x[1]))
2、进行合并
主要思路为res为当前维护的列表,如果不为空,
就和待考查列表a中的值进行操作;
如果为空就先加入一个a中待考察的列表(一般就是加入第一个)

n =int(input())
a =[ ]
res = []

for _ in range(n):
    l,r = map(int,input().split())
    a.append([l,r])
# 先根据0,再根据1排序
a = sorted(a,key=lambda x:(x[0],x[1]))

for i in range(n):
    if res:
        if res[-1][1] >= a[i][0]:
            res[-1][1] = max(res[-1][1],a[i][1])
        else:
            res.append([a[i][0],a[i][1]])
    else:
        res.append([a[0][0],a[0][1]])
print(len(res))

785

1、别忘了边界判断
2、快排是从l-1和r+1开始的
3、递归时右边界为j

def quick_sort(q,l,r):
    if l>=r:
        return
    i,j = l-1,r+1
    x = q[l+r>>1]
    while i<j:
        i+=1
        j-=1
        while q[i]<x:
            i += 1
        while q[j]>x:
            j -= 1
        if i<j: q[i],q[j]=q[j],q[i]
        
    quick_sort(q,l,j)
    quick_sort(q,j+1,r)
n = int(input())
nums = list(map(int,input().split()))
quick_sort(nums,0,n-1)
print(' '.join(map(str,nums)))

786

j换成i就会有问题。

弄了半天,不知道为什么

def quick_sort(q,l,r,k):
    if l>=r:
        return q[l]
    i,j=l-1,r+1
    x = q[l+r>>1]
    while i<j:
        i +=1
        j -=1
        while q[i]<x:
            i+=1
        while q[j]>x:
            j-=1
        if i<j:
            q[i],q[j]=q[j],q[i]
    sl = j-l+1
    if k<=sl:
        return quick_sort(q,l,j,k)
    else:
        return quick_sort(q,j+1,r,k-sl)
        
n,k = map(int,input().split())
nums = list(map(int,input().split()))
print(quick_sort(nums,0,n-1,k))

787

1、i=l;j=mid+1

2、切片操作赋值!!需要多出来一个:
q[l:r+1],是r+1才能到r!!!

def merge_sort(q,l,r):
    if l>=r:
        return
    mid = l+r>>1
    i,j=l,mid+1
    a=[]

    merge_sort(q,l,mid)
    merge_sort(q,mid+1,r)
    while i<=mid and j<=r:
        if q[i]<=q[j]:
            a.append(q[i])
            i+=1
        else:
            a.append(q[j])
            j+=1
    if i<=mid:
        a += q[i:mid+1]
    if j<=r:
        a += q[j:r+1]
    q[l:r+1] = a[:]
    
n = int(input())
nums=list(map(int,input().split()))
merge_sort(nums,0,n-1)
print(' '.join(map(str,nums)))

788

1、加入tmp后别忘了,给i、j+1
2、函数要return res作为结果。

def merge_sort(q,l,r):
    if l>=r:
        return 0
    mid =l+r>>1
    res = merge_sort(q,l,mid)+merge_sort(q,mid+1,r)
    
    i,j=l,mid+1
    tmp = []
    while i<=mid and j<=r:
        if q[i]<=q[j]:
            tmp.append(q[i])
            i+=1
        else:
            tmp.append(q[j])
            res += mid-i+1
            j+=1
    if i<=mid:
        tmp += q[i:mid+1]
    if j<=r:
        tmp += q[j:r+1]
    
    q[l:r+1]=tmp[:]
    return res
n = int(input())
nums=list(map(int,input().split()))
print(merge_sort(nums,0,n-1))

789

二分后l和r应该是相同的,取哪个都行

def binary_left_search(q,l,r,k):
    while l<r:
        mid = l+r>>1
        if q[mid]>=k:
            r = mid
        else:
            l = mid+1
    if q[l]==k:
        return l
    else:
        return -1
        
def binary_right_search(q,l,r,k):
    while l<r:
        mid = l+r+1>>1
        if q[mid]<=k:
            l=mid
        else:
            r = mid-1
    if q[r]==k:
        return r
    else:
        return -1
n,q = map(int,input().split())
nums = list(map(int,input().split()))
while q!=0:
    q-=1
    k = int(input())
    a1 = binary_left_search(nums,0,n-1,k)
    a2 = binary_right_search(nums,0,n-1,k)
    print(a1,a2)

790

1、注意print时候的格式:f和.format()
2、是r-l,不是l-r

def binary_search(n):
    l,r=-100.0,100.0
    while r-l>=1e-8:
        mid = (l+r)/2
        if mid**3>=n:
            r = mid
        else:
            l = mid
    print(':.6f'.format(l))
n = float(input())
binary_search(n)

795

挺顺利的,前缀和,下标从1开始。

n,m = map(int,input().split())
nums = [0]+list(map(int,input().split()))

s = [0]*100010

for i in range(1,n+1):
    s[i] = s[i-1]+nums[i]

for _ in range(m):
    l,r = map(int,input().split())
    print(s[r]-s[l-1])

796

输入A矩阵的时候,我们需要用A【i】【1:】=

其他的比较顺利

n,m,q = map(int,input().split())

A = [[0]*1010 for _ in range(1010)]
S = [[0]*1010 for _ in range(1010)]

for i in range(1,n+1):
    A[i][1:] = list(map(int,input().split()))

for i in range(1,n+1):
    for j in range(1,m+1):
        S[i][j] = S[i-1][j]+S[i][j-1]-S[i-1][j-1]+A[i][j]

for _ in range(q):
    x1,y1,x2,y2 = list(map(int,input().split()))
    print(S[x2][y2]+S[x1-1][y1-1]-S[x1-1][y2]-S[x2][y1-1])

797

有点遗忘了,不过写的很顺滑。查分就是构造一个数组,使其前缀和为原来的数组,这样在一段上的改变可以用O(1)来实现。

n,m=map(int,input().split())
nums =[0]+list(map(int,input().split()))

def insert(l,r,c):
    B[l] += c
    B[r+1] -= c
B = [0]*100010

for i in range(1,n+1):
    insert(i,i,nums[i])

for _ in range(m):
    l,r,c = map(int,input().split())
    insert(l,r,c)

for j in range(1,n+1):
    B[j] += B[j-1]
    print(B[j],end=' ')

798

也是比较顺畅的,开了一个最大的空间,而不是动态的空间。

n,m,q = map(int,input().split())
A = [[0]*1010 for _ in range(1010)]
B = [[0]*1010 for _ in range(1010)]
def insert(x1,y1,x2,y2,c):
    B[x1][y1] += c
    B[x1][y2+1] -= c
    B[x2+1][y1] -= c
    B[x2+1][y2+1] += c

for i in range(1,n+1):
    A[i][1:]=list(map(int,input().split()))

for i in range(1,n+1):
    for j in range(1,m+1):
        insert(i,j,i,j,A[i][j])
        
for _ in range(q):
    x1,y1,x2,y2,c = map(int,input().split())
    insert(x1,y1,x2,y2,c)
    
for i in range(1,n+1):
    for j in range(1,m+1):
        B[i][j] += B[i-1][j]+B[i][j-1]-B[i-1][j-1]
        print(B[i][j],end=' ')
    print()

799

很吃力:
相当于记录以每个i为结尾的不重复的最长子串长度,然后选最长值。
具体方法:
先读到i,一旦有重复的,则缩短j,直到不重复,记录当前长度,把长的放入res中。若读到i没有重复值,则就可直接比较。

n = int(input())
a = list(map(int,input().split()))
#暴力算法:i指向第几位;j用来判断是否有重复;
#双指针单调性:i向右走,j不可能向左走。
i,j,res=0,0,0
index = [0]*100010

while i<n:
    index[a[i]]+=1
    while j<i and index[a[i]]==2:
        index[a[j]]-=1
        j+=1
    res = max(res,i-j+1)
    i+=1
print(res)

总结

写到这里也结束了,在文章最后放上一个小小的福利,以下为小编自己在学习过程中整理出的一个关于 java开发 的学习思路及方向。从事互联网开发,最主要的是要学好技术,而学习技术是一条慢长而艰苦的道路,不能靠一时激情,也不是熬几天几夜就能学好的,必须养成平时努力学习的习惯,更加需要准确的学习方向达到有效的学习效果。

由于内容较多就只放上一个大概的大纲,需要更及详细的学习思维导图的 点击我的Gitee获取
还有 高级java全套视频教程 java进阶架构师 视频+资料+代码+面试题!

全方面的java进阶实践技术资料,并且还有技术大牛一起讨论交流解决问题。

以上是关于D5-AcWing-8002816801803+复习785-799的主要内容,如果未能解决你的问题,请参考以下文章

希望开复老师早日康复

删除复选标记

使用 Modal Segue 保留复选标记

复平面中的旋转矩阵

酉相合与复对称矩阵

在collectionview上显示复选标记