#include <iostream>
#include <string>
using namespace std;

struct Node{     			//структура звена списка 
	int value;				//передаваемое значение
	Node *next, *prev;		//указатели на следующий и предыдущий элементы
};

struct deque{
	Node *head=nullptr;		//инициализация начала и конца списка, размера дека 
	Node *tail=nullptr;
	int count=0;
	void push_back(int num){
		Node* element=new Node; //выделение памяти под новый элемент структуры
		element->value=num;		//добавляем значение в структуру
		count++;
		if(!head){				//если список пуск
			head=element;		//т.к элемент эдинственный, 
			tail=head;			//он является и хвостом и головой
		}
		else{
			element->prev=tail; //предыдущий элемент списка относительно добавленного, будет последним(хвостом)
			tail->next=element; //следующий элемент за хвостом это добавляемый элемент списка
			tail=element;		//присваивание элементу статуса хвоста
		}
		cout<<"ok"<<endl;
	}
	void push_front(int num){
		Node *element=new Node;
		element->value=num;
		count++;
		if(!head){
			head=element;
			tail=head;
		}
		else{
			element->next=head;		//следующий элемент за добавляемым элементом является хвост
			head->prev=element;		//перед головой находится добавляемый элемент
			head=element;			//присваивание элементу статуса головы
		}
		cout<<"ok"<<endl;
	}
	void pop_back(){
		if(count!=0){				//если дек не пустой
			cout<<tail->value<<endl;
			if(count>1){			//если в деке находится больше одного элемента
				Node *element=tail; //указываем на то, что будет использоваться хвост
				tail=tail->prev;	//присваиваем статус хвоста предыдущему элементу
				tail->next=nullptr; //указываем на то, что за элементом пусто
				delete element;		//удаляем бывший хвост
				count--;			//уменьшаем размер дека
			}
			else{					//если в деке находится всего один элемент
				head=tail=0;		//присваиваем ему значение ноль
				count--;			//уменьшаем размер дека
			}
		}
		else cout<<"error"<<endl;
	}
	void pop_front(){
		if(count!=0){
			cout<<head->value<<endl;
			if(head->next){			//если в деке больше одного элемента 
				Node *element=head;	//указываем на то, что будем использовать голову
				head=head->next;	//присваиваем статус головы следующему за бывшей головой элементу 
				head->prev=nullptr;	//указываем на то, что перед головой пусто
				delete element;		//удаляем бывшую голову
				count--;			//уменьшаем размер дека
			}
			else if(head==tail){	//если элемент один в деке
				head->next=nullptr;	//указываем, что за головой пусто
				head=nullptr;		//указываем на то, что голова тоже пуста
				delete head;		//удаляем единственный элемент
				count=0;			//присваиваем ноль размеру дека
			}
		}
		else cout<<"error"<<endl;
	}
	void back(){
		if(count!=0)cout<<tail->value<<endl; //выводим значение хвоста
		else cout<<"error"<<endl;
	}
	void front(){
		if(count!=0)cout<<head->value<<endl; //выводим значение головы
		else cout<<"error"<<endl;
	}
	void size(){
		cout<<count<<endl;		//выводим размер дека
	}
	void clear(){
		count=0;				//присваиваем размеру дека ноль
		cout<<"ok"<<endl;
		while(head) 			//цикл: пока по адресу головы что-то лежит
     {
         tail=head->next; 		//присваиваем статус хвоста следующему элементу, что лежит за головой 
         delete head; 			//удаляем первый элемент дека
         head=tail; 			//указываем на то, что хвост принимает статус головы
     }
	}
	void exit(){
		cout<<"bye";
	}
};

int main() {
	deque deq;
	string str;
	while(cin>>str){
		if(str=="push_front"){
			int num;
			cin>>num;
			deq.push_front(num);
		}
		if(str=="push_back"){
			int num;
			cin>>num;
			deq.push_back(num);
		}
		if(str=="pop_front")deq.pop_front();
		if(str=="pop_back")deq.pop_back();
		if(str=="clear")deq.clear();
		if(str=="size")deq.size();
		if(str=="front")deq.front();
		if(str=="back")deq.back();
		if(str=="exit"){
			deq.exit();
			break;
		}
	}
	return 0;
}