开始

最近在学习Netty,其核心便是基于Java的NIO编程封装而来,这篇文章对NIO编程的原理进行介绍,并提供一个NIO编程的完整实践案例。

阅读全文 »

题目描述

假设按照升序排序的数组在预先未知的某个点上进行了旋转。( 例如,数组 [0,1,2,4,5,6,7] 可能变为 [4,5,6,7,0,1,2] )。搜索一个给定的目标值,如果数组中存在这个目标值,则返回它的索引,否则返回 -1 。你可以假设数组中不存在重复的元素。你的算法时间复杂度必须是 O(log n) 级别。

分析

该题有两个关键点:

  1. 如何理解旋转:题中的旋转是在一个旋转,所以对于数组如[1,2,3],不存在类似这样的旋转结果:[3,2,1]
  2. 要求时间复杂度为 O(logn),很容易想到应该用二分法,但关键在于如何讨论出所有可能情况。

解题思路

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
class Solution {
public int search(int[] nums, int target) {
//二分查找:分三种情况,左边有序,右边有序,左右都有序
//使用位运算代替乘除法(常用的优化办法)
int len = nums.length;
int left = 0;
int right = len-1;
if(len == 0)
return -1;
int mid;
while(left<=right){
mid = (left+right)>>1;
if(nums[mid]==target)
return mid;
else if(nums[left]<=nums[mid]&&nums[mid]<=nums[right]){//左右都有序
if(target>nums[mid])
left = mid + 1;
else
right = mid - 1;
}
else if(nums[left]<=nums[mid]&&nums[mid]>=nums[right]){//左边有序,右边无序
if(target>nums[mid])
left = mid + 1;
else if(target<nums[mid]&&target<nums[left])
left = mid + 1;
else
right = mid - 1;
}
else if(nums[left]>=nums[mid]&&nums[mid]<=nums[right]){//左边无序,右边有序
if(target<nums[mid])
right = mid - 1;
else if(target>nums[mid]&&target>nums[right])
right = mid - 1;
else
left = mid + 1;
}
}
return -1;
}
}

最后

不得不说位运算是个神器,时间消耗只有传统乘除法的1/4,同时位运算也是实现乘除法的一种办法。

题目描述

给定一个 haystack 字符串和一个 needle 字符串,在 haystack 字符串中找出 needle 字符串出现的第一个位置 (从0开始)。如果不存在,则返回 -1。

阅读全文 »

策略

  • 不要选择劣势策略。
  • 理性的选择导致非最优结果。
  • 想获得某些事物之前必定要试图做/了解他。
  • 站在别人的立场上分析他们会怎么做。
  • 耶鲁大学的学生很自私(2333)。

写在最前

心血来潮,都二十多岁的人了还没有一个自己的博客,确实说不过去,最近因为疫情原因也确实有了有史以来最长的一个寒假,除了学习+玩耍,我发现我越来越想要留下些属于自己的印记,或是记录,或是分享。不管怎么样,这是真正动笔的第一篇blog,一个全新的开始,加油吧!

阅读全文 »