双指针 
      
    
      
      
      
        栈 
      
    
      
      
      
        链表 
      
    
   
  
    
      
       
     
  
  
    
      
    
    
      
       
     
  
    
题目描述 
在一个大小为 n 且 n 为 偶数  的链表中,对于 0 <= i <= (n / 2) - 1 的 i ,第 i 个节点(下标从 0  开始)的孪生节点为第 (n-1-i) 个节点 。
    比方说,n = 4 那么节点 0 是节点 3 的孪生节点,节点 1 是节点 2 的孪生节点。这是长度为 n = 4  的链表中所有的孪生节点。 
 
孪生和  定义为一个节点和它孪生节点两者值之和。
给你一个长度为偶数的链表的头节点 head ,请你返回链表的 最大孪生和  。
 
示例 1: 
输入: head = [5,4,2,1]
输出: 6
解释: 
节点 0 和节点 1 分别是节点 3 和 2 的孪生节点。孪生和都为 6 。
链表中没有其他孪生节点。
所以,链表的最大孪生和是 6 。
 
示例 2: 
输入: head = [4,2,2,3]
输出: 7
解释: 
链表中的孪生节点为:
- 节点 0 是节点 3 的孪生节点,孪生和为 4 + 3 = 7 。
- 节点 1 是节点 2 的孪生节点,孪生和为 2 + 2 = 4 。
所以,最大孪生和为 max(7, 4) = 7 。
 
示例 3: 
输入: head = [1,100000]
输出: 100001
解释: 
链表中只有一对孪生节点,孪生和为 1 + 100000 = 100001 。
 
 
提示: 
    链表的节点数目是 [2, 105 ] 中的 偶数  。 
    1 <= Node.val <= 105  
 
解法 
方法一:模拟 
我们可以将链表中的节点值依次存入数组中,然后使用双指针分别指向数组的开头和结尾,计算每对孪生节点的孪生和,取最大值即为答案。
时间复杂度 \(O(n)\) ,空间复杂度 \(O(n)\) 。其中 \(n\)  是链表的节点数。
Python3 Java C++ Go TypeScript Rust 
 1 
 2 
 3 
 4 
 5 
 6 
 7 
 8 
 9 
10 
11 
12 
13 # Definition for singly-linked list. 
# class ListNode: 
#     def __init__(self, val=0, next=None): 
#         self.val = val 
#         self.next = next 
class   Solution : 
    def   pairSum ( self ,  head :  Optional [ ListNode ])  ->  int : 
        s  =  [] 
        while  head : 
            s . append ( head . val ) 
            head  =  head . next 
        n  =  len ( s ) 
        return  max ( s [ i ]  +  s [ - ( i  +  1 )]  for  i  in  range ( n  >>  1 )) 
 
 
 1 
 2 
 3 
 4 
 5 
 6 
 7 
 8 
 9 
10 
11 
12 
13 
14 
15 
16 
17 
18 
19 
20 
21 
22 
23 /** 
 * Definition for singly-linked list. 
 * public class ListNode { 
 *     int val; 
 *     ListNode next; 
 *     ListNode() {} 
 *     ListNode(int val) { this.val = val; } 
 *     ListNode(int val, ListNode next) { this.val = val; this.next = next; } 
 * } 
 */ 
class  Solution   { 
     public   int   pairSum ( ListNode   head )   { 
         List < Integer >   s   =   new   ArrayList <> (); 
         for   (;   head   !=   null ;   head   =   head . next )   { 
             s . add ( head . val ); 
         } 
         int   ans   =   0 ,   n   =   s . size (); 
         for   ( int   i   =   0 ;   i   <   ( n   >>   1 );   ++ i )   { 
             ans   =   Math . max ( ans ,   s . get ( i )   +   s . get ( n   -   1   -   i )); 
         } 
         return   ans ; 
     } 
} 
 
 
 1 
 2 
 3 
 4 
 5 
 6 
 7 
 8 
 9 
10 
11 
12 
13 
14 
15 
16 
17 
18 
19 
20 /** 
 * Definition for singly-linked list. 
 * struct ListNode { 
 *     int val; 
 *     ListNode *next; 
 *     ListNode() : val(0), next(nullptr) {} 
 *     ListNode(int x) : val(x), next(nullptr) {} 
 *     ListNode(int x, ListNode *next) : val(x), next(next) {} 
 * }; 
 */ 
class   Solution   { 
public : 
     int   pairSum ( ListNode *   head )   { 
         vector < int >   s ; 
         for   (;   head   !=   nullptr ;   head   =   head -> next )   s . push_back ( head -> val ); 
         int   ans   =   0 ,   n   =   s . size (); 
         for   ( int   i   =   0 ;   i   <   ( n   >>   1 );   ++ i )   ans   =   max ( ans ,   s [ i ]   +   s [ n   -   i   -   1 ]); 
         return   ans ; 
     } 
}; 
 
 
 1 
 2 
 3 
 4 
 5 
 6 
 7 
 8 
 9 
10 
11 
12 
13 
14 
15 
16 
17 
18 
19 
20 /** 
 * Definition for singly-linked list. 
 * type ListNode struct { 
 *     Val int 
 *     Next *ListNode 
 * } 
 */ 
func   pairSum ( head   * ListNode )   int   { 
     var   s   [] int 
     for   ;   head   !=   nil ;   head   =   head . Next   { 
         s   =   append ( s ,   head . Val ) 
     } 
     ans ,   n   :=   0 ,   len ( s ) 
     for   i   :=   0 ;   i   <   ( n   >>   1 );   i ++   { 
         if   ans   <   s [ i ] + s [ n - i - 1 ]   { 
             ans   =   s [ i ]   +   s [ n - i - 1 ] 
         } 
     } 
     return   ans 
} 
 
 
 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 /** 
 * Definition for singly-linked list. 
 * class ListNode { 
 *     val: number 
 *     next: ListNode | null 
 *     constructor(val?: number, next?: ListNode | null) { 
 *         this.val = (val===undefined ? 0 : val) 
 *         this.next = (next===undefined ? null : next) 
 *     } 
 * } 
 */ 
function   pairSum ( head :   ListNode   |   null ) :   number   { 
     const   arr   =   []; 
     let   node   =   head ; 
     while   ( node )   { 
         arr . push ( node . val ); 
         node   =   node . next ; 
     } 
     const   n   =   arr . length ; 
     let   ans   =   0 ; 
     for   ( let   i   =   0 ;   i   <   n   >>   1 ;   i ++ )   { 
         ans   =   Math . max ( ans ,   arr [ i ]   +   arr [ n   -   1   -   i ]); 
     } 
     return   ans ; 
} 
 
 
 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 // Definition for singly-linked list. 
// #[derive(PartialEq, Eq, Clone, Debug)] 
// pub struct ListNode { 
//   pub val: i32, 
//   pub next: Option<Box<ListNode>> 
// } 
// 
// impl ListNode { 
//   #[inline] 
//   fn new(val: i32) -> Self { 
//     ListNode { 
//       next: None, 
//       val 
//     } 
//   } 
// } 
impl   Solution   { 
     pub   fn   pair_sum ( head :   Option < Box < ListNode >> )   ->   i32   { 
         let   mut   arr   =   Vec :: new (); 
         let   mut   node   =   & head ; 
         while   node . is_some ()   { 
             let   t   =   node . as_ref (). unwrap (); 
             arr . push ( t . val ); 
             node   =   & t . next ; 
         } 
         let   n   =   arr . len (); 
         let   mut   ans   =   0 ; 
         for   i   in   0 .. n   >>   1   { 
             ans   =   ans . max ( arr [ i ]   +   arr [ n   -   1   -   i ]); 
         } 
         ans 
     } 
} 
 
 
 
 
方法二:快慢指针 + 反转链表 + 双指针 
时间复杂度 \(O(n)\) ,空间复杂度 \(O(1)\) 。
Python3 Java C++ Go TypeScript 
 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 # Definition for singly-linked list. 
# class ListNode: 
#     def __init__(self, val=0, next=None): 
#         self.val = val 
#         self.next = next 
class   Solution : 
    def   pairSum ( self ,  head :  Optional [ ListNode ])  ->  int : 
        def   reverse ( head ): 
            dummy  =  ListNode () 
            curr  =  head 
            while  curr : 
                next  =  curr . next 
                curr . next  =  dummy . next 
                dummy . next  =  curr 
                curr  =  next 
            return  dummy . next 
        slow ,  fast  =  head ,  head . next 
        while  fast  and  fast . next : 
            slow ,  fast  =  slow . next ,  fast . next . next 
        pa  =  head 
        q  =  slow . next 
        slow . next  =  None 
        pb  =  reverse ( q ) 
        ans  =  0 
        while  pa  and  pb : 
            ans  =  max ( ans ,  pa . val  +  pb . val ) 
            pa  =  pa . next 
            pb  =  pb . next 
        return  ans 
 
 
 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 
41 
42 
43 /** 
 * Definition for singly-linked list. 
 * public class ListNode { 
 *     int val; 
 *     ListNode next; 
 *     ListNode() {} 
 *     ListNode(int val) { this.val = val; } 
 *     ListNode(int val, ListNode next) { this.val = val; this.next = next; } 
 * } 
 */ 
class  Solution   { 
     public   int   pairSum ( ListNode   head )   { 
         ListNode   slow   =   head ; 
         ListNode   fast   =   head . next ; 
         while   ( fast   !=   null   &&   fast . next   !=   null )   { 
             slow   =   slow . next ; 
             fast   =   fast . next . next ; 
         } 
         ListNode   pa   =   head ; 
         ListNode   q   =   slow . next ; 
         slow . next   =   null ; 
         ListNode   pb   =   reverse ( q ); 
         int   ans   =   0 ; 
         while   ( pa   !=   null )   { 
             ans   =   Math . max ( ans ,   pa . val   +   pb . val ); 
             pa   =   pa . next ; 
             pb   =   pb . next ; 
         } 
         return   ans ; 
     } 
     private   ListNode   reverse ( ListNode   head )   { 
         ListNode   dummy   =   new   ListNode (); 
         ListNode   curr   =   head ; 
         while   ( curr   !=   null )   { 
             ListNode   next   =   curr . next ; 
             curr . next   =   dummy . next ; 
             dummy . next   =   curr ; 
             curr   =   next ; 
         } 
         return   dummy . next ; 
     } 
} 
 
 
 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 
41 
42 
43 
44 /** 
 * Definition for singly-linked list. 
 * struct ListNode { 
 *     int val; 
 *     ListNode *next; 
 *     ListNode() : val(0), next(nullptr) {} 
 *     ListNode(int x) : val(x), next(nullptr) {} 
 *     ListNode(int x, ListNode *next) : val(x), next(next) {} 
 * }; 
 */ 
class   Solution   { 
public : 
     int   pairSum ( ListNode *   head )   { 
         ListNode *   slow   =   head ; 
         ListNode *   fast   =   head -> next ; 
         while   ( fast   &&   fast -> next )   { 
             slow   =   slow -> next ; 
             fast   =   fast -> next -> next ; 
         } 
         ListNode *   pa   =   head ; 
         ListNode *   q   =   slow -> next ; 
         slow -> next   =   nullptr ; 
         ListNode *   pb   =   reverse ( q ); 
         int   ans   =   0 ; 
         while   ( pa )   { 
             ans   =   max ( ans ,   pa -> val   +   pb -> val ); 
             pa   =   pa -> next ; 
             pb   =   pb -> next ; 
         } 
         return   ans ; 
     } 
     ListNode *   reverse ( ListNode *   head )   { 
         ListNode *   dummy   =   new   ListNode (); 
         ListNode *   curr   =   head ; 
         while   ( curr )   { 
             ListNode *   next   =   curr -> next ; 
             curr -> next   =   dummy -> next ; 
             dummy -> next   =   curr ; 
             curr   =   next ; 
         } 
         return   dummy -> next ; 
     } 
}; 
 
 
 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 /** 
 * Definition for singly-linked list. 
 * type ListNode struct { 
 *     Val int 
 *     Next *ListNode 
 * } 
 */ 
func   pairSum ( head   * ListNode )   int   { 
     reverse   :=   func ( head   * ListNode )   * ListNode   { 
         dummy   :=   & ListNode {} 
         curr   :=   head 
         for   curr   !=   nil   { 
             next   :=   curr . Next 
             curr . Next   =   dummy . Next 
             dummy . Next   =   curr 
             curr   =   next 
         } 
         return   dummy . Next 
     } 
     slow ,   fast   :=   head ,   head . Next 
     for   fast   !=   nil   &&   fast . Next   !=   nil   { 
         slow ,   fast   =   slow . Next ,   fast . Next . Next 
     } 
     pa   :=   head 
     q   :=   slow . Next 
     slow . Next   =   nil 
     pb   :=   reverse ( q ) 
     ans   :=   0 
     for   pa   !=   nil   { 
         ans   =   max ( ans ,   pa . Val + pb . Val ) 
         pa   =   pa . Next 
         pb   =   pb . Next 
     } 
     return   ans 
} 
 
 
 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 /** 
 * Definition for singly-linked list. 
 * class ListNode { 
 *     val: number 
 *     next: ListNode | null 
 *     constructor(val?: number, next?: ListNode | null) { 
 *         this.val = (val===undefined ? 0 : val) 
 *         this.next = (next===undefined ? null : next) 
 *     } 
 * } 
 */ 
function   pairSum ( head :   ListNode   |   null ) :   number   { 
     let   fast   =   head ; 
     let   slow   =   head ; 
     while   ( fast )   { 
         fast   =   fast . next . next ; 
         slow   =   slow . next ; 
     } 
     let   prev   =   null ; 
     while   ( slow )   { 
         const   next   =   slow . next ; 
         slow . next   =   prev ; 
         prev   =   slow ; 
         slow   =   next ; 
     } 
     let   left   =   head ; 
     let   right   =   prev ; 
     let   ans   =   0 ; 
     while   ( left   &&   right )   { 
         ans   =   Math . max ( ans ,   left . val   +   right . val ); 
         left   =   left . next ; 
         right   =   right . next ; 
     } 
     return   ans ; 
} 
 
 
 
 
  
  
  
    
    
    
    
      
  
    
      
  
     
   
  GitHub