Skip to content

Instantly share code, notes, and snippets.

@wulinjie122
Created September 19, 2020 00:52
Show Gist options
  • Save wulinjie122/54034f30261c528d546c331725cc51b6 to your computer and use it in GitHub Desktop.
Save wulinjie122/54034f30261c528d546c331725cc51b6 to your computer and use it in GitHub Desktop.
2020 SAP中国研究院面试题
1. 实现一个静态方法,输入参数n,返回计算结果n!(即n的阶乘),用两种方式实现,一种是循环,一种是递归,注意不要数组越界。
2. 输入一个字符串,比如"abcdef",实现一个方法,可以反转字符串,返回"fedcba",不可以借助jdk自带的方法和其他开源工具。
3. 用Java实现一个单例模式,比如类Singleton,常见如饿汉模式或者 懒汉模式,网上可以找到很多例子,并且能当场解释为什么需要用volatile关键字,懂内存屏障和防CPU指令重排,说得出Java内存模型的原理。
public class SingletonClass { 

  private volatile static SingletonClass instance = null; 

  public static SingletonClass getInstance() { 
    if (instance == null) { 
      synchronized (SingletonClass.class) { 
        if(instance == null) { 
          instance = new SingletonClass(); 
        } 
      } 
    } 
    return instance; 
  } 
  private SingletonClass() { 
  } 
}
4.输入两个单调递增的链表,输出两个链表合成后的链表,当然我们需要合成后的链表满足单调不减规则。

方法一(递归) 合并过程中,首先比较两个链表的首节点哪个小,较小的节点作为合成链表的首节点,之后将指针指向较小节点的后一个节点,再次进行上面逻辑的比较,可以发现比较过程是一个递归的操作。

public ListNode Merge(ListNode list1,ListNode list2) {
    	
    	if(list2 == null) {
    		return list1;
    	}
    	else if(list1 == null) {
    		return list2;
    	}
    	
    	ListNode listAll = null;
    	
    	if(list1.val < list2.val) {
    		listAll = list1;
    		listAll.next = Merge(list1.next, list2);
    	}
    	else {
    		listAll = list2;
    		listAll.next = Merge(list1, list2.next);
    	}

    	return listAll;
    	
    }

通过递归到最大的节点,并进行返回递归操作到上一次递归的空间,将返回节点作为当前次大节点的下一个节点,这样从后到前返回到第一个节点的空间,递归操作完成。

方法二(非递归)

public ListNode Merge_2(ListNode list1,ListNode list2) {
    	if(list2 == null) {
    		return list1;
    	}
    	else if(list1 == null) {
    		return list2;
    	}
    	
    	ListNode mergeHead = new ListNode(0);
    	ListNode current = mergeHead;
    	
    	while(list1 != null && list2 != null) {
    		if(list1.val < list2.val) {
    			current.next = list1;
    			list1 = list1.next;
    		}
    		else {
    			current.next = list2;
    			list2 = list2.next;
    		}
    		
    		current = current.next;
    	}
    	
    	if(list1 == null) {
    		current.next = 	list2;
    	}
    	
    	if(list2 == null) {
    		current.next = list1;
    	}
    	
    	return mergeHead.next;

    }

注意声明mergeHead来作为合成链表的头结点,声明current来作为一个当前合成链表最后一个节点的指针,初始化指向头结点,之后比较两个链表对应元素大小,并修改两个两个链表和current的指针指向。

5. 有两张表,A1表和A2表,如果A2表中找不到记录,则返回"name2 not provided",如果找到了记录,则返回 a1.id, a1.name, a2.name2,

A1表如下:

ID NAME
1 张三
2 李四
3 王五
4 赵六

A2表如下:

ID NAME2
2 李四
4 赵六

查询结果示例:

ID NAME NAME2
1 张三 name2 not provided
2 李四 李四
3 王五 name2 not provided
4 赵六 赵六
6. table中有4列,其中id, name, content, mark表示唯一记录,删除重复的记录,仅保留一条即可。

| id | name | content| mark | | -------- | -----: |-----: | | 1| 张三|aaa|bbb| | 2| 张三|aaa|bbb| | 3| 张三|aaa|bbb| | 4| 李四|ccc|eee| | 5| 李四|ccc|eee|

# 排除法,删除每个分组下其他的ID,仅保留最小的id即可
delete from table 
where id not in (
  select min(id) from table
  group by name, content, mark
)
7. table中有1000条记录,按照name排序,获取第300-400条记录(mysql或者oracle实现都可以)。
select * from table
order by name
limit 300,400
8. 如下table,有id, name, city, department, age几个字段,按照city、department分组,获取平均年龄,并按照平均年龄正序排列,平均年龄最小的排在最上面。
id name city department age
1 张三 上海 市场部 25
2 李四 上海 市场部 30
3 王五 上海 市场部 50
4 赵六 北京 技术部 35
5 王梅梅 北京 技术部 40
6 李雷 北京 技术部 60
7 冯绍峰 郑州 业务部 33
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment