leecode更新
This commit is contained in:
parent
e6858db144
commit
ebbaae5e7f
|
|
@ -9,6 +9,33 @@
|
|||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>junit</groupId>
|
||||
<artifactId>junit</artifactId>
|
||||
<version>4.13.2</version>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>junit</groupId>
|
||||
<artifactId>junit</artifactId>
|
||||
<version>4.13.2</version>
|
||||
<scope>compile</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.projectlombok</groupId>
|
||||
<artifactId>lombok</artifactId>
|
||||
<version>RELEASE</version>
|
||||
<scope>compile</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>junit</groupId>
|
||||
<artifactId>junit</artifactId>
|
||||
<version>4.13.1</version>
|
||||
<scope>compile</scope>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
<artifactId>DataStructures</artifactId>
|
||||
<build>
|
||||
<plugins>
|
||||
|
|
|
|||
|
|
@ -0,0 +1,73 @@
|
|||
package com.atguigu.sort.selftry;
|
||||
|
||||
import org.junit.Test;
|
||||
|
||||
import java.util.Arrays;
|
||||
|
||||
/**
|
||||
*@BelongsProject: DataStructures_Algorithm
|
||||
*@BelongsPackage: com.atguigu.sort.selftry
|
||||
*@Author: markilue
|
||||
*@CreateTime: 2023-03-31 10:26
|
||||
*@Description: TODO 尝试堆排序
|
||||
*@Version: 1.0
|
||||
*/
|
||||
public class HeapSort {
|
||||
|
||||
@Test
|
||||
public void test(){
|
||||
int[] arr = {20, 50, 45, 40, 35,10,30,15,25};
|
||||
//测试80000个数据进行测试
|
||||
// int[] arr = new int[200];
|
||||
// for (int i = 0; i < arr.length; i++) {
|
||||
// arr[i] = (int) (Math.random() * 200); //生成一个[0,80000]的数
|
||||
// }
|
||||
heapSort(arr);
|
||||
System.out.println(Arrays.toString(arr));
|
||||
}
|
||||
|
||||
|
||||
public void heapSort(int[] arr) {
|
||||
|
||||
if (arr == null) return;
|
||||
//从最后一个非叶子节点开始进行堆化
|
||||
for (int i = arr.length / 2 - 1; i >= 0; i--) {
|
||||
adjustHeap(arr, i, arr.length);
|
||||
}
|
||||
|
||||
//进行交换
|
||||
int temp;
|
||||
for (int i = arr.length - 1; i > 0; i--) {
|
||||
temp = arr[i];
|
||||
arr[i] = arr[0];
|
||||
arr[0] = temp;
|
||||
adjustHeap(arr, 0, i);//把交换完的i放在合适的位置
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
public void adjustHeap(int[] arr, int i, int length) {
|
||||
|
||||
int temp = arr[i];//记录下以前位置的值
|
||||
|
||||
for (int j = 2 * i + 1; j < length; j++) {
|
||||
//比较左右节点哪一个更大
|
||||
if (j + 1 < length && arr[j] < arr[j + 1]) {
|
||||
j++;
|
||||
}
|
||||
if (arr[j] > temp) {
|
||||
//需要进行交换
|
||||
arr[i] = arr[j];
|
||||
i = j;//后续比较j位置的值了
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
arr[i] = temp;//找到合适的位置放temp
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
|
@ -1,5 +1,7 @@
|
|||
package com.atguigu.tree;
|
||||
|
||||
import org.junit.Test;
|
||||
|
||||
import java.text.SimpleDateFormat;
|
||||
import java.util.Arrays;
|
||||
import java.util.Date;
|
||||
|
|
@ -17,44 +19,57 @@ public class HeapSort {
|
|||
// System.out.println(Arrays.toString(arr));
|
||||
|
||||
//测试80000个数据进行测试
|
||||
int[] arr =new int[8000000];
|
||||
int[] arr = new int[8000000];
|
||||
for (int i = 0; i < arr.length; i++) {
|
||||
arr[i] = (int)(Math.random()*8000000); //生成一个[0,80000]的数
|
||||
arr[i] = (int) (Math.random() * 8000000); //生成一个[0,80000]的数
|
||||
}
|
||||
Date date1 = new Date();
|
||||
SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
|
||||
String date1Str = simpleDateFormat.format(date1);
|
||||
System.out.println("排序前的时间:"+date1Str); //排序前的时间:2022-02-15 21:19:36
|
||||
System.out.println("排序前的时间:" + date1Str); //排序前的时间:2022-02-15 21:19:36
|
||||
|
||||
heapSort(arr);
|
||||
Date date2 = new Date();
|
||||
String date2Str = simpleDateFormat.format(date2);
|
||||
System.out.println("排序后的时间:"+date2Str); //排序后的时间:2022-02-15 21:19:40
|
||||
System.out.println("排序后的时间:" + date2Str); //排序后的时间:2022-02-15 21:19:40
|
||||
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void test() {
|
||||
int[] arr = {20, 50, 45, 40, 35,10,30,15,25};
|
||||
//测试80000个数据进行测试
|
||||
// int[] arr = new int[200];
|
||||
// for (int i = 0; i < arr.length; i++) {
|
||||
// arr[i] = (int) (Math.random() * 200); //生成一个[0,80000]的数
|
||||
// }
|
||||
heapSort(arr);
|
||||
System.out.println(Arrays.toString(arr));
|
||||
}
|
||||
|
||||
/**
|
||||
* 编写一个堆排序的方法
|
||||
*/
|
||||
public static void heapSort(int[] arr) {
|
||||
|
||||
//TODO (1)将无序序列构建成一个堆,根据升序降序需求选择大顶堆或者小顶堆
|
||||
//arr.length/2-1求出来的是完全二叉树的最后一个非叶子节点
|
||||
for (int i = arr.length/2-1; i >= 0; i--) {
|
||||
adjustHeap(arr,i,arr.length);
|
||||
// arr.length/2-1求出来的是完全二叉树的最后一个非叶子节点;
|
||||
// arr.length/2-1是关键,是adjustHeap前提的满足条件的前提
|
||||
for (int i = arr.length / 2 - 1; i >= 0; i--) {
|
||||
adjustHeap(arr, i, arr.length);
|
||||
}
|
||||
|
||||
|
||||
int temp=0;
|
||||
int temp = 0;
|
||||
//TODO (2)将顶对元素与末尾元素交换,将最大元素放置在数组末尾
|
||||
//TODO (3)重新调整结构,使其满足堆定义,然后继续交换对顶元素与当前末尾元素,贩毒执行调整+交换步骤,直到整个序列有序
|
||||
for (int i = arr.length-1; i >0; i--) {
|
||||
//TODO (3)重新调整结构,使其满足堆定义,然后继续交换对顶元素与当前末尾元素,反复执行调整+交换步骤,直到整个序列有序
|
||||
for (int i = arr.length - 1; i > 0; i--) {
|
||||
//交换
|
||||
temp=arr[i];
|
||||
arr[i]=arr[0];
|
||||
arr[0]=temp;
|
||||
adjustHeap(arr,0,i);
|
||||
temp = arr[i];
|
||||
arr[i] = arr[0];
|
||||
arr[0] = temp;
|
||||
adjustHeap(arr, 0, i);//主要就是利用堆顶元素就是最大值来进行处理的
|
||||
|
||||
}
|
||||
|
||||
|
|
@ -62,7 +77,7 @@ public class HeapSort {
|
|||
}
|
||||
|
||||
/**
|
||||
* 前提:该节点的所有子节点都已经是大顶堆了
|
||||
* TODO 前提:该节点的所有子节点都已经是大顶堆了,因为这里需要break
|
||||
* 将以第i个位置为根节点时以下树,调整成一个大顶堆
|
||||
*
|
||||
* @param arr 待调整的数组
|
||||
|
|
@ -76,20 +91,22 @@ public class HeapSort {
|
|||
//开始调整
|
||||
//说明:j = i * 2 + 1 ;这里k就是i节点的左子节点
|
||||
for (int j = i * 2 + 1; j < length; j = j * 2 + 1) {
|
||||
//TODO 1.寻找左右节点哪一个更大
|
||||
if (j + 1 < length && arr[j] < arr[j + 1]) {
|
||||
//左子节点的值小于右子节点的值
|
||||
j++; //j指向右子节点
|
||||
}
|
||||
//TODO 2.用左右节点中大值去和他的父节点比较;如果小了直接将父节点变成那个最大的值
|
||||
if (arr[j] > temp) {
|
||||
//如果子节点大于父节点
|
||||
arr[i] = arr[j];//把较大的值赋给当前节点
|
||||
i = j; //将i指向j,继续循环比较
|
||||
}else {
|
||||
break;
|
||||
} else {
|
||||
break;//左右子节点都比父节点小,直接break
|
||||
}
|
||||
}
|
||||
//当for循环结束后,我们已经将以i为父节点的树的最大值,放在了i的位置
|
||||
arr[i]=temp; //将temp值放在调整后的位置
|
||||
arr[i] = temp; //将temp值放在调整后的位置
|
||||
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -0,0 +1,72 @@
|
|||
package com.markilue.leecode.hot100;
|
||||
|
||||
import org.junit.Test;
|
||||
|
||||
import java.util.Arrays;
|
||||
|
||||
/**
|
||||
*@BelongsProject: Leecode
|
||||
*@BelongsPackage: com.markilue.leecode.hot100
|
||||
*@Author: markilue
|
||||
*@CreateTime: 2023-03-30 10:14
|
||||
*@Description:
|
||||
* TODO 力扣300 最长递增子序列:
|
||||
* 给你一个整数数组 nums ,找到其中最长严格递增子序列的长度。
|
||||
* 子序列 是由数组派生而来的序列,删除(或不删除)数组中的元素而不改变其余元素的顺序。例如,[3,6,2,7] 是数组 [0,3,1,6,2,2,7] 的子序列。
|
||||
*@Version: 1.0
|
||||
*/
|
||||
public class T78_LengthOfLIS {
|
||||
|
||||
@Test
|
||||
public void test() {
|
||||
// int[] nums={10,9,2,5,3,7,101,18};
|
||||
int[] nums = {1, 3, 6, 7, 9, 4, 10, 5, 6};
|
||||
System.out.println(lengthOfLIS(nums));
|
||||
}
|
||||
|
||||
/**
|
||||
* 思路:dp
|
||||
* dp[i]表示以0开头以i结尾的数组的最长递增子序列长度
|
||||
* @param nums
|
||||
* @return
|
||||
*/
|
||||
public int lengthOfLIS(int[] nums) {
|
||||
|
||||
int[] dp = new int[nums.length];
|
||||
Arrays.fill(dp, 1);
|
||||
int max = 0;
|
||||
|
||||
|
||||
for (int i = 1; i < dp.length; i++) {
|
||||
for (int j = 0; j < i; j++) {
|
||||
if (nums[i] > nums[j]) {
|
||||
dp[i] = Math.max(dp[i], dp[j] + 1);
|
||||
}
|
||||
if (max < dp[i]) max = dp[i];
|
||||
}
|
||||
}
|
||||
return max;
|
||||
}
|
||||
|
||||
|
||||
public int lengthOfLIS1(int[] nums) {
|
||||
int N = nums.length;
|
||||
//end[i]表示i+1长度的递增子序列的最小值
|
||||
int[] end = new int[N];
|
||||
end[0] = nums[0];
|
||||
int index = 0;
|
||||
for(int i=1; i< N;i++){
|
||||
if(nums[i] > end[index]){
|
||||
end[++index] = nums[i];
|
||||
} else {
|
||||
for (int j = 0; j <= index; j++) {
|
||||
if (nums[i] <= end[j]) {
|
||||
end[j] = nums[i];//替换对应的位置
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return index + 1;
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,241 @@
|
|||
package com.markilue.leecode.hot100;
|
||||
|
||||
import org.junit.Test;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
*@BelongsProject: Leecode
|
||||
*@BelongsPackage: com.markilue.leecode.hot100
|
||||
*@Author: markilue
|
||||
*@CreateTime: 2023-03-30 10:36
|
||||
*@Description:
|
||||
* TODO 力扣301 删除无效的括号:
|
||||
* 给你一个由若干括号和字母组成的字符串 s ,删除最小数量的无效括号,使得输入的字符串有效。
|
||||
* 返回所有可能的结果。答案可以按 任意顺序 返回。
|
||||
*@Version: 1.0
|
||||
*/
|
||||
public class T79_RemoveInvalidParentheses {
|
||||
|
||||
|
||||
//不知道该怎么去重,就用set存储结果 18ms
|
||||
Set<String> set = new HashSet<>();
|
||||
StringBuilder str;
|
||||
|
||||
public List<String> removeInvalidParentheses(String s) {
|
||||
int lmove = 0;
|
||||
int rmove = 0;
|
||||
str = new StringBuilder(s);
|
||||
//遍历一遍,求出要删除左括号和右括号的数量
|
||||
for (int i = 0; i < s.length(); i++) {
|
||||
if (s.charAt(i) == '(') {
|
||||
lmove++;
|
||||
} else if (s.charAt(i) == ')') {
|
||||
//左右括号可以匹配
|
||||
if (lmove > 0) {
|
||||
lmove--;
|
||||
} else {
|
||||
rmove++;
|
||||
}
|
||||
}
|
||||
}
|
||||
dfs(lmove, rmove, 0);
|
||||
return new ArrayList<>(set);
|
||||
}
|
||||
|
||||
public void dfs(int lmove, int rmove, int i) {
|
||||
if (lmove == 0 && rmove == 0) {
|
||||
//判断字符串内括号是否有效
|
||||
if (isValid(str)) {
|
||||
set.add(new String(str.toString()));
|
||||
}
|
||||
return;
|
||||
}
|
||||
//还需要删除的括号个数 小于 能过删除的字符个数
|
||||
if (lmove + rmove > str.length() - i) {
|
||||
return;
|
||||
}
|
||||
//不删除
|
||||
dfs(lmove, rmove, i + 1);
|
||||
|
||||
//删除,分左右括号考虑
|
||||
if (str.charAt(i) == '(' && lmove > 0) {
|
||||
str.deleteCharAt(i);//删除
|
||||
dfs(lmove - 1, rmove, i);//进入下一层,因为删除了i处括号,所以不需要i+1
|
||||
str.insert(i, '(');//恢复现场
|
||||
} else if (str.charAt(i) == ')' && rmove > 0) {
|
||||
str.deleteCharAt(i);//删除
|
||||
dfs(lmove, rmove - 1, i);//进入下一层
|
||||
str.insert(i, ')');//恢复现场
|
||||
}
|
||||
}
|
||||
|
||||
public boolean isValid(StringBuilder str) {
|
||||
int left = 0;
|
||||
for (int i = 0; i < str.length(); i++) {
|
||||
if (str.charAt(i) == '(') {
|
||||
left++;
|
||||
} else if (str.charAt(i) == ')') {
|
||||
left--;
|
||||
}
|
||||
if (left < 0) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
//自己去重4ms
|
||||
private List<String> res = new ArrayList<String>();
|
||||
|
||||
public List<String> removeInvalidParentheses1(String s) {
|
||||
int lremove = 0;
|
||||
int rremove = 0;
|
||||
|
||||
for (int i = 0; i < s.length(); i++) {
|
||||
if (s.charAt(i) == '(') {
|
||||
lremove++;
|
||||
} else if (s.charAt(i) == ')') {
|
||||
if (lremove == 0) {
|
||||
rremove++;
|
||||
} else {
|
||||
lremove--;
|
||||
}
|
||||
}
|
||||
}
|
||||
helper(s, 0, lremove, rremove);
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
private void helper(String str, int start, int lremove, int rremove) {
|
||||
if (lremove == 0 && rremove == 0) {
|
||||
if (isValid(str)) {
|
||||
res.add(str);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
for (int i = start; i < str.length(); i++) {
|
||||
if (i != start && str.charAt(i) == str.charAt(i - 1)) {
|
||||
continue;
|
||||
}
|
||||
// 如果剩余的字符无法满足去掉的数量要求,直接返回
|
||||
if (lremove + rremove > str.length() - i) {
|
||||
return;
|
||||
}
|
||||
// 尝试去掉一个左括号
|
||||
if (lremove > 0 && str.charAt(i) == '(') {
|
||||
helper(str.substring(0, i) + str.substring(i + 1), i, lremove - 1, rremove);
|
||||
}
|
||||
// 尝试去掉一个右括号
|
||||
if (rremove > 0 && str.charAt(i) == ')') {
|
||||
helper(str.substring(0, i) + str.substring(i + 1), i, lremove, rremove - 1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private boolean isValid(String str) {
|
||||
int cnt = 0;
|
||||
for (int i = 0; i < str.length(); i++) {
|
||||
if (str.charAt(i) == '(') {
|
||||
cnt++;
|
||||
} else if (str.charAt(i) == ')') {
|
||||
cnt--;
|
||||
if (cnt < 0) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return cnt == 0;
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void test(){
|
||||
String s ="()())()";
|
||||
System.out.println(removeInvalidParentheses2(s));
|
||||
}
|
||||
|
||||
|
||||
//自己尝试一遍
|
||||
public List<String> removeInvalidParentheses2(String s) {
|
||||
|
||||
//统计需要去掉的左括号和右括号的数量
|
||||
|
||||
int left = 0;
|
||||
int right = 0;
|
||||
|
||||
for (char c : s.toCharArray()) {
|
||||
if (c == '(') {
|
||||
left++;
|
||||
} else if (c == ')') {
|
||||
if (left == 0) {
|
||||
right++;
|
||||
} else {
|
||||
left--;
|
||||
}
|
||||
}
|
||||
}
|
||||
helper1(s, left, right, 0);
|
||||
return res;
|
||||
|
||||
}
|
||||
|
||||
public void helper1(String s, int left, int right, int start) {
|
||||
if (left == 0 && right == 0) {
|
||||
if (isValid1(s)) {
|
||||
res.add(s);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
for (int i = start; i < s.length(); i++) {
|
||||
//去重
|
||||
if (i != start && s.charAt(i) == s.charAt(i - 1)) continue;
|
||||
|
||||
if (left + right > s.length() - i) {
|
||||
//怎么删都不够了
|
||||
return;
|
||||
}
|
||||
|
||||
//尝试删除左括号
|
||||
if (left > 0 && s.charAt(i) == '(') {
|
||||
helper1(s.substring(0, i) + s.substring(i + 1), left - 1, right, i + 1);
|
||||
}
|
||||
|
||||
//尝试删除右括号
|
||||
if (right > 0 && s.charAt(i) == ')') {
|
||||
helper1(s.substring(0, i) + s.substring(i + 1), left, right - 1, i + 1);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public boolean isValid1(String s) {
|
||||
int left = 0;
|
||||
for (char c : s.toCharArray()) {
|
||||
if (c == '(') {
|
||||
left++;
|
||||
} else if (c == ')') {
|
||||
if (left == 0) {
|
||||
return false;
|
||||
} else {
|
||||
left--;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return left==0;
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,70 @@
|
|||
package com.markilue.leecode.hot100;
|
||||
|
||||
import org.junit.Test;
|
||||
|
||||
/**
|
||||
*@BelongsProject: Leecode
|
||||
*@BelongsPackage: com.markilue.leecode.hot100
|
||||
*@Author: markilue
|
||||
*@CreateTime: 2023-03-31 11:13
|
||||
*@Description: TODO
|
||||
*@Version: 1.0
|
||||
*/
|
||||
public class T80_MaxProfit {
|
||||
|
||||
@Test
|
||||
public void test() {
|
||||
int[] prices = {1, 2, 3, 0, 2};
|
||||
System.out.println(maxProfit(prices));
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* 动态dp,状态分为三种:
|
||||
* 今天手里没有股票且不在冷冻期dp[i][0]
|
||||
* 今天手里没有股票且在冷冻期dp[i][1]
|
||||
* 今天手里有股票dp[i][2]
|
||||
* @param prices
|
||||
* @return
|
||||
*/
|
||||
public int maxProfit(int[] prices) {
|
||||
if (prices.length == 1) return 0;
|
||||
|
||||
int[][] dp = new int[prices.length][3];
|
||||
|
||||
dp[0][0] = 0;
|
||||
dp[0][1] = 0;
|
||||
dp[0][2] = -prices[0];
|
||||
|
||||
for (int i = 1; i < prices.length; i++) {
|
||||
dp[i][0] = Math.max(dp[i - 1][0], dp[i - 1][1]);//昨天是冷冻期;或者昨天也没买
|
||||
dp[i][1] = dp[i - 1][2] + prices[i];//必须是今天买入
|
||||
dp[i][2] = Math.max(dp[i - 1][2], dp[i - 1][0] - prices[i]);//必须是今天买入
|
||||
}
|
||||
|
||||
return Math.max(dp[dp.length - 1][0], dp[dp.length - 1][1]);
|
||||
|
||||
}
|
||||
|
||||
//滚动数组优化
|
||||
public int maxProfit1(int[] prices) {
|
||||
if (prices.length == 1) return 0;
|
||||
|
||||
|
||||
int dp0 = 0;
|
||||
int dp1 = 0;
|
||||
int dp2 = -prices[0];
|
||||
|
||||
for (int i = 1; i < prices.length; i++) {
|
||||
int temp = dp0;
|
||||
dp0 = Math.max(dp0, dp1);//昨天是冷冻期;或者昨天也没买
|
||||
dp1 = dp2 + prices[i];//必须是今天买入
|
||||
dp2 = Math.max(dp2, temp - prices[i]);//必须是今天买入
|
||||
}
|
||||
|
||||
return Math.max(dp0, dp1);
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,120 @@
|
|||
package com.markilue.leecode.hot100;
|
||||
|
||||
import org.junit.Test;
|
||||
|
||||
/**
|
||||
*@BelongsProject: Leecode
|
||||
*@BelongsPackage: com.markilue.leecode.hot100
|
||||
*@Author: markilue
|
||||
*@CreateTime: 2023-03-31 11:28
|
||||
*@Description: TODO
|
||||
*@Version: 1.0
|
||||
*/
|
||||
public class T81_MaxCoins {
|
||||
|
||||
@Test
|
||||
public void test() {
|
||||
int[] nums = {3, 1, 5, 8};
|
||||
System.out.println(maxCoins1(nums));
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* 思路:优先戳中间最小的
|
||||
* 不对
|
||||
* @param nums
|
||||
* @return
|
||||
*/
|
||||
public int maxCoins(int[] nums) {
|
||||
|
||||
int result = 0;
|
||||
int count = nums.length;
|
||||
|
||||
while (nums[0] != -1) {
|
||||
int minIndex = 0;
|
||||
int threshold = nums.length;
|
||||
|
||||
if (count == 3) {
|
||||
boolean flag = false;
|
||||
for (int i = 0; i < nums.length; i++) {
|
||||
if (nums[i] == -1) {
|
||||
threshold = i;
|
||||
break;
|
||||
}
|
||||
if (nums[i] == 1) {
|
||||
minIndex = i;
|
||||
flag = true;
|
||||
}
|
||||
|
||||
}
|
||||
if (!flag) {
|
||||
minIndex = 1;
|
||||
}
|
||||
}else {
|
||||
for (int i = 1; i < nums.length; i++) {
|
||||
if (nums[i] == -1) {
|
||||
threshold = i;
|
||||
break;
|
||||
}
|
||||
if (nums[minIndex] > nums[i]) {
|
||||
minIndex = i;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//戳i位置
|
||||
int left;
|
||||
if (minIndex - 1 < 0) {
|
||||
left = 1;
|
||||
} else {
|
||||
left = nums[minIndex - 1];
|
||||
}
|
||||
|
||||
int right;
|
||||
if (minIndex + 1 >= threshold) {
|
||||
right = 1;
|
||||
} else {
|
||||
right = nums[minIndex + 1];
|
||||
}
|
||||
result += left * nums[minIndex] * right;
|
||||
System.arraycopy(nums, minIndex + 1, nums, minIndex, threshold - minIndex - 1);
|
||||
nums[threshold - 1] = -1;
|
||||
count--;
|
||||
}
|
||||
|
||||
return result;
|
||||
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* 官方动态规划法:
|
||||
* dp[i][j]表示填满开区间(i,j)能得到的最多硬币数
|
||||
* 最终答案即为 dp[0][n+1]dp[0][n+1]dp[0][n+1]。实现时要注意到动态规划的次序。
|
||||
* 动态规划:
|
||||
* 速度击败27.13% 内存击败45.56% 43ms
|
||||
* @param nums
|
||||
* @return
|
||||
*/
|
||||
public int maxCoins1(int[] nums) {
|
||||
int n = nums.length;
|
||||
int[][] rec = new int[n + 2][n + 2];
|
||||
int[] val = new int[n + 2];
|
||||
val[0] = val[n + 1] = 1;
|
||||
for (int i = 1; i <= n; i++) {
|
||||
val[i] = nums[i - 1];
|
||||
}
|
||||
for (int i = n - 1; i >= 0; i--) {
|
||||
for (int j = i + 2; j <= n + 1; j++) {
|
||||
for (int k = i + 1; k < j; k++) {
|
||||
int sum = val[i] * val[k] * val[j];//计算戳当前点的sum
|
||||
sum += rec[i][k] + rec[k][j];//计算不要这个点之后的左右点的戳开的和
|
||||
rec[i][j] = Math.max(rec[i][j], sum);
|
||||
}
|
||||
}
|
||||
}
|
||||
return rec[0][n + 1];
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -15,6 +15,16 @@ import java.util.ArrayList;
|
|||
*/
|
||||
public class test {
|
||||
|
||||
static {
|
||||
|
||||
|
||||
System.out.println("hello sta");
|
||||
}
|
||||
|
||||
public static void main(String[] args) {
|
||||
System.out.println("hello world");
|
||||
}
|
||||
|
||||
|
||||
//测试ArrayList的index是否发生变化
|
||||
@Test
|
||||
|
|
|
|||
|
|
@ -1,6 +1,7 @@
|
|||
package com.markilue.leecode.test;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.*;
|
||||
|
||||
import java.util.Scanner;
|
||||
|
||||
/**
|
||||
|
|
@ -14,53 +15,53 @@ import java.util.Scanner;
|
|||
public class testAnt {
|
||||
|
||||
|
||||
public static void main(String[] args) {
|
||||
|
||||
Scanner sc = new Scanner(System.in);
|
||||
String input = sc.nextLine();
|
||||
|
||||
new testAnt().test(input);
|
||||
// StringBuilder output = new StringBuilder();
|
||||
// int left = 0;
|
||||
// public static void main(String[] args) {
|
||||
//
|
||||
// //去除前面的
|
||||
// while (left < input.length() && input.charAt(left) == ' ') {
|
||||
// left++;
|
||||
// }
|
||||
// Scanner sc = new Scanner(System.in);
|
||||
// String input = sc.nextLine();
|
||||
//
|
||||
// boolean isCapital = true; // 首字母是否大写
|
||||
// for (int i = left; i < input.length(); i++) {
|
||||
// char c = input.charAt(i);
|
||||
// if (c == ' ') {
|
||||
// if (i > 0 && input.charAt(i - 1) == '.') {
|
||||
// output.deleteCharAt(output.length() - 1);
|
||||
// }
|
||||
// // 跳过多余的空格
|
||||
// while (i < input.length() - 1 && input.charAt(i + 1) == ' ') {
|
||||
// i++;
|
||||
// }
|
||||
// if (input.charAt(i + 1) != '.') {
|
||||
// output.append(' ');
|
||||
// }
|
||||
// } else if (c == '.') {
|
||||
// // 句号后面要加一个空格
|
||||
// output.append(". ");
|
||||
// isCapital = true; // 下一句话的首字母要大写
|
||||
// } else {
|
||||
// if (isCapital) {
|
||||
// // 首字母要大写
|
||||
// output.append(Character.toUpperCase(c));
|
||||
// isCapital = false;
|
||||
// } else {
|
||||
// output.append(c);
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// new testAnt().test(input);
|
||||
//// StringBuilder output = new StringBuilder();
|
||||
//// int left = 0;
|
||||
////
|
||||
//// //去除前面的
|
||||
//// while (left < input.length() && input.charAt(left) == ' ') {
|
||||
//// left++;
|
||||
//// }
|
||||
////
|
||||
//// boolean isCapital = true; // 首字母是否大写
|
||||
//// for (int i = left; i < input.length(); i++) {
|
||||
//// char c = input.charAt(i);
|
||||
//// if (c == ' ') {
|
||||
//// if (i > 0 && input.charAt(i - 1) == '.') {
|
||||
//// output.deleteCharAt(output.length() - 1);
|
||||
//// }
|
||||
//// // 跳过多余的空格
|
||||
//// while (i < input.length() - 1 && input.charAt(i + 1) == ' ') {
|
||||
//// i++;
|
||||
//// }
|
||||
//// if (input.charAt(i + 1) != '.') {
|
||||
//// output.append(' ');
|
||||
//// }
|
||||
//// } else if (c == '.') {
|
||||
//// // 句号后面要加一个空格
|
||||
//// output.append(". ");
|
||||
//// isCapital = true; // 下一句话的首字母要大写
|
||||
//// } else {
|
||||
//// if (isCapital) {
|
||||
//// // 首字母要大写
|
||||
//// output.append(Character.toUpperCase(c));
|
||||
//// isCapital = false;
|
||||
//// } else {
|
||||
//// output.append(c);
|
||||
//// }
|
||||
//// }
|
||||
//// }
|
||||
////
|
||||
//// System.out.println(output.toString());
|
||||
// sc.close();
|
||||
//
|
||||
// System.out.println(output.toString());
|
||||
sc.close();
|
||||
|
||||
}
|
||||
// }
|
||||
|
||||
|
||||
public void test(String str) {
|
||||
|
|
@ -106,4 +107,68 @@ public class testAnt {
|
|||
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
// public static void main(String[] args) {
|
||||
// Scanner scanner = new Scanner(System.in);
|
||||
// int k = scanner.nextInt();
|
||||
// int count = 0;
|
||||
// for (int i = 0; i < 65536; i++) {
|
||||
// String hex = String.format("%04x", i); // 将整数转换成长度为 4 的十六进制数
|
||||
// if (isGoodHex(hex)) {
|
||||
// count++;
|
||||
// if (count == k) {
|
||||
// System.out.println(hex);
|
||||
// break;
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// public static boolean isGoodHex(String hex) {
|
||||
// Set<Character> digits = new HashSet<>();
|
||||
// for (char c : hex.toCharArray()) {
|
||||
// digits.add(c);
|
||||
// }
|
||||
// return digits.size() == 4;
|
||||
// }
|
||||
|
||||
|
||||
public static void main(String[] args) {
|
||||
String s = "????(?"; // 待匹配的字符串
|
||||
int left = 0, right = 0, count = 0; // 分别记录左括号、右括号和合法的括号对的数量
|
||||
Stack<Integer> stack = new Stack<>(); // 栈,用于记录左括号和 '?' 的下标
|
||||
for (int i = 0; i < s.length(); i++) {
|
||||
char c = s.charAt(i);
|
||||
if (c == '(' || c == '?') {
|
||||
stack.push(i);
|
||||
if (c == '(') {
|
||||
left++;
|
||||
}
|
||||
} else {
|
||||
if (stack.isEmpty()) {
|
||||
continue;
|
||||
}
|
||||
stack.pop();
|
||||
if (c == ')') {
|
||||
right++;
|
||||
}
|
||||
count++;
|
||||
}
|
||||
}
|
||||
while (!stack.isEmpty()) { // 处理剩余的左括号或 '?'
|
||||
int index = stack.pop();
|
||||
if (s.charAt(index) == '(') {
|
||||
left--;
|
||||
} else {
|
||||
right--;
|
||||
}
|
||||
}
|
||||
count += Math.min(left, right); // '?' 可以代替左括号或右括号,因此左右括号数量较小的值为合法的括号对数量
|
||||
System.out.println(count);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue