Go: package main

import (
	"bufio"
	"os"
	"strconv"
	"fmt"
)

var scanner = bufio.NewScanner(os.Stdin)
const INF = 0x7fffffff
func main() {
	S := 17
	seat := make([][]int, 27)
	for i :=range seat {
		seat[i] = make([]int, 27)
	}
	ans := make([]int, 105)
	id := 0
	Q := make([][]int, 0)
	for i := 0; i < S; i++ {
		seat[i][0] = -1
	}
	t := -1
	for ans[99] == 0 {
		t++
		if  t%5 == 0 && id <= 99 {
			if id % 5 == 1 {
				n := 5
				tmp := []int{id, n, t}
				Q = append(Q, tmp)
				id++
			} else {
				n := 2
				tmp := []int{id, n, t}
				Q = append(Q, tmp)
				id++
			}
		}
		for i := 0; i < 5; i++ {
			if seat[i][1] == 0 {
				continue
			}
			seat[i][1]--
			if seat[i][1] == 0 {
				seat[i][0] = -1
			}
		}
		f := len(Q)
		for f > 0 {
			i, n := Q[0][0], Q[0][1]
			f = 0
			for j := 0; j < S; j++ {
				g := 0
				for k := 0; k < n; k++ {
					if seat[j+k][0] >= 0 {
						g = 1
						break
					}
				}
				if g != 0 {
					continue
				}
				ans[i] = t-Q[0][2]
				Q = Q[1:]
				f = len(Q)
				for k := 0; k < n; k++ {
					seat[j+k][0] = i
					seat[j+k][1] = 17*(i&1) + 3*(i%3) + 19
				}
				break
			}
		}
	}
	for scanner.Scan() {
		n, _ := strconv.Atoi(scanner.Text())
		fmt.Println(ans[n])
	}
}

C++: #include <iostream>
#include <cstdio>
#include <vector>
#include <map>
#include <queue>
#include <algorithm>
using namespace std;

typedef pair<int,int> P;
// (時刻,イベント,グループ番号)の組を表す.
// イベントは 離席 or 着席 を -1 or 1 で表す.
typedef pair< int , P > State;

// グループ番号 i の人数を返す.
int get_num(int i){
	return (i%5 == 1)? 5 : 2 ;
}

// グループ id が座れるかどうか返す. 座れる時はsekiの状態も変わる.
bool check(vector<int>& seki , int id ){
	int num = get_num(id);
	for(int i=0 ; i < 17 ; i++ ){
		if( num == 2 ){
			if( i+1 < 17 && seki[i] == -1 && seki[i+1] == -1 ){
				seki[i] = seki[i+1] = id;
				return true;
			}
		}else{
			if( i+4 < 17 && seki[i] == -1 && seki[i+1] == -1 && seki[i+2] == -1 && seki[i+3] == -1 && seki[i+4] == -1 ){
				seki[i] = seki[i+1] = seki[i+2] = seki[i+3] = seki[i+4] = id;
				return true;
			}
		}
	}
	return false;
}

// グループ id を離席させる. 離席するとsekiの状態も変わる.
void remove(vector<int>& seki , int id ){
	for(int i=0 ; i < 17 ; i++ ){
		if( seki[i] == id ) seki[i] = -1;
	}
}

int main(){
	// (時刻,イベント,グループ番号) の組を保持し, 時刻の早いほうから処理する.
	priority_queue< State , vector<State> , greater<State> > q;
	// (グループ番号,到着時刻) の組を保持し, 今並んでいる人々を表す.
	for(int i=0 ; i < 100 ; i++ ){
		q.push( State( 5*i , P(+1,i) ) );
	}
	// seki[i] := i番目の席に座っている人の番号, 座ってないときは -1
	vector<int> seki(17);
	for(int i=0 ; i < 17 ; i++ ) seki[i] = -1;
	
	// que := 待ち行列, (グループ番号を保持する)
	queue<int> que;
	
	// wait[i] := グループ i の待ち時間
	int wait[100] = {0}; 
	
	while( !q.empty() ){
		int t = q.top().first;
		int event = q.top().second.first;
		int id = q.top().second.second;
		q.pop();
		
		/*printf("%3d : ", t);
		for(int i=0 ; i < 17 ; i++ ){
			if( seki[i] == -1 ){
				printf("__");
			}else{
				printf("%2d", seki[i] );
			}
		}*/
		
		
		// グループ id が着席するとき 
		if( event == 1 ){
			
			// 行列があるとき
			if( !que.empty() ){
				que.push( id );
				
				//printf(": %d is wait! \n", id);
			}else if( check( seki , id ) ){// 座れるかチェック, 座れなかったら行列に並ぶ.
				int eat_time = 17 * (id%2) + 3 * (id%3) + 19;
				q.push( State( t + eat_time , P(-1,id) ) );
				
				//printf(": %d is sit! \n", id);
			}else{
				que.push( id );
				
				//printf(": %d is wait! \n", id);
			}
		}else{ // グループ id が離席するとき
			remove( seki , id );
			//printf(": %d is leave! ", id);
			// 行列の先頭の人が座れるかチェック
			bool flag = false;
			do{
				if( que.empty() ) break;
				flag = false;
				int id_2 = que.front();
				if( check( seki , id_2 ) ){
					flag = true;
					int eat_time = 17 * (id_2%2) + 3 * (id_2%3) + 19;
					q.push( State( t + eat_time , P(-1,id_2) ) );
					wait[id_2] = t - id_2 * 5;
					que.pop();
					//printf("&& %d is sit! ", id_2);
				}
			}while( flag );
			//puts("");
		}
	}
	int n;
	while( cin >> n ){
		cout << wait[n] << endl;
	}
}

C++: #include <iostream>
#include <vector>
#include <queue>
#include <map>
#include <algorithm>
using namespace std;

int search_sequence(vector<int> &a,int n){
	int cnt=0;
	for(int i=0;i<a.size();++i){
		if(a[i]==-1)++cnt;
		else cnt=0;
		if(cnt>=n)return i-cnt+1;
	}
	return -1;
}

int main(void){
    vector<int> seat(17,-1);
    int time[100],finish[100];
    queue<pair<int,int> > q;
    int x=0,y=0;
    for(int t=0;y<100;++t){
      if(t%5==0) q.push(make_pair(x++,(x%5==1)?5:2));
      for(int i=0;i<17;++i){
        if(seat[i]!=-1&&finish[seat[i]]==t){
        	fill(&seat[i],&seat[i+((seat[i]%5==1)?5:2)],-1);
        	//cerr<<t<<":";for(int i=0;i<17;++i)cerr<<seat[i]<<((i!=16)?" ":"\n");
      	}
      }
      while(search_sequence(seat,q.front().second)!=-1){
        fill(&seat[search_sequence(seat,q.front().second)],&seat[search_sequence(seat,q.front().second)+q.front().second],q.front().first);
        //cerr<<t<<":";for(int i=0;i<17;++i)cerr<<seat[i]<<((i!=16)?" ":"\n");
        finish[q.front().first]=t+17*(q.front(
        ).first%2)+3*(q.front().first%3)+19;
        time[q.front().first]=t-5*q.front().first;
        q.pop();++y;
      }
    }
  int n;
  while(cin>>n){
  	cout<<time[n]<<endl;
  }
  return 0;
}

C++: #include <bits/stdc++.h>

using namespace std;

#define REP(i,a,b) for(int i=a;i<b;i++)
#define rep(i,n) REP(i,0,n)

#define MP make_pair
#define F first
#define S second

enum { INQ, SIT, LEAVE };
int now; bool fiveempty, twoempty;
int ans[100], seats[17];
map<int, deque<pair<int, int> > > mp;
inline int num(int i) {return i%5==1?5:2;}
inline int eattime(int i) {return 17*(i%2)+3*(i%3)+19;}

void update_emptyseats() {
  bool fe = 0, te = 0;
  rep(i, 13)
    if(seats[i]==-1 &&
       seats[i+1]==-1 &&
       seats[i+2]==-1 &&
       seats[i+3]==-1 &&
       seats[i+4]==-1) { fe = 1; }
  rep(i, 16)
    if(seats[i]==-1 && seats[i+1]==-1) { te = 1; }
  fiveempty = fe, twoempty = te;
}

void sit(int id) {
  ans[id] = now-5*id;
  mp[now+eattime(id)].push_front(MP(id, (int)LEAVE));
  
  if(num(id) == 5) rep(i, 13)
                     if(seats[i]==-1 &&
                        seats[i+1]==-1 &&
                        seats[i+2]==-1 &&
                        seats[i+3]==-1 &&
                        seats[i+4]==-1) {
                       rep(j, 5) seats[i+j] = id;
                       update_emptyseats(); return;
                     }
  
  if(num(id) == 2) rep(i, 16)
                     if(seats[i]==-1 && seats[i+1]==-1) {
                       rep(j, 2) seats[i+j] = id;
                       update_emptyseats(); return;
                     } 
}

void leave(int id) {
  rep(i, 17) {
    if(seats[i] == id) {
      rep(j, num(id)) { seats[i+j] = -1; }
      update_emptyseats();
      return;
    }
  }
}

int main() {
  
  rep(i, 100) mp[5*i].push_back(MP(i, (int)INQ));
  queue<int> waitingQ;
  fiveempty = twoempty = 1;
  memset(seats, -1, sizeof seats);
  while(!mp.empty()) {
    now = mp.begin()->F;
    deque<pair<int, int> >& Q = mp.begin()->S;
    int id = Q.front().F;
    int act = Q.front().S; Q.pop_front();
    if(act == SIT) {
      sit(id);
      if( !waitingQ.empty()
          && ( (num(waitingQ.front()) == 5 && fiveempty)
               || (num(waitingQ.front()) == 2 && twoempty) )
      ) {
        Q.push_front(MP(waitingQ.front(), (int)SIT));
        waitingQ.pop();
      }
    }
    else if(act == INQ) {
      if(!waitingQ.empty()) { waitingQ.push(id); }
      else if(num(id) == 5 && fiveempty) { sit(id); }
      else if(num(id) == 2 && twoempty) { sit(id); }
      else { waitingQ.push(id); }
    }
    else if(act == LEAVE) {
      leave(id);
      if( !waitingQ.empty()
          && ( (num(waitingQ.front()) == 5 && fiveempty)
               || (num(waitingQ.front()) == 2 && twoempty) )
      ) { Q.push_front(MP(waitingQ.front(), (int)SIT)); waitingQ.pop(); }
    }
    if(Q.empty()) mp.erase(mp.begin());
  }
  for(int N; cin >> N;) cout << ans[N] << endl;
  
  return 0;
}