optiver笔试——20190406

两个笔试都是在HackerRank上做的

一、trading system engineer笔试

一个小时的时间,30道选择题,4道编程题,实在做不完

编程题主要是考,linux命令,python命令和语法,剩下的还考算法、数据结构等等。

第一道编程题,是读入一个txt文件名,里面存有三类文件:

  • .c(C)
  • .cpp(C++)
  • .cs(C#)

让你写个程序把这三类文件分开,存进三个txt里

filename = "1.txt"
fr=open(filename)
line=fr.readline()
newc=open("c_"+filename,"a+")
newcp=open("cpp_"+filename,"a+")
newcs=open("cs_"+filename,"a+")
while line:
    print(line)
    if(line.endswith(".c\n")or(line.endswith(".c"))):
        newc.write(line)
    elif(line.endswith(".cpp\n")or(line.endswith(".cpp"))):
        newcp.write(line)
    else:
        newcs.write(line)
    line=fr.readline()
fr.close()
newc.close()
newcp.close()
newcs.close()

第二题第三题又臭又长,也全是英文,没来得及做

第四题,让你实现floor

直接

import math

return math.floor(a+b)

就过了

二、developer笔试

2个小时,2道编程题,说是这两道题原本给时间90min就能做完,之所以给你2h,是为了让你写出高效的优美的代码

第一题:

定义了一个新的日历

#include <bits/stdc++.h>

using namespace std;

string ltrim(const string &);
string rtrim(const string &);



/*
 * Complete the 'find_settlement_date' function below.
 *
 * The function is expected to return a STRING.
 * The function accepts following parameters:
 *  1. STRING trade_date
 *  2. STRING_ARRAY holidays
 */

string find_settlement_date(string trade_date, vector<string> holidays) {
    
}

int main()
{
    ofstream fout(getenv("OUTPUT_PATH"));

    string trade_date;
    getline(cin, trade_date);

    string holidays_count_temp;
    getline(cin, holidays_count_temp);

    int holidays_count = stoi(ltrim(rtrim(holidays_count_temp)));

    vector<string> holidays(holidays_count);

    for (int i = 0; i < holidays_count; i++) {
        string holidays_item;
        getline(cin, holidays_item);

        holidays[i] = holidays_item;
    }

    string result = find_settlement_date(trade_date, holidays);

    fout << result << "\n";

    fout.close();

    return 0;
}

string ltrim(const string &str) {
    string s(str);

    s.erase(
        s.begin(),
        find_if(s.begin(), s.end(), not1(ptr_fun<int, int>(isspace)))
    );

    return s;
}

string rtrim(const string &str) {
    string s(str);

    s.erase(
        find_if(s.rbegin(), s.rend(), not1(ptr_fun<int, int>(isspace))).base(),
        s.end()
    );

    return s;
}

 中规中矩的日历经典问题,没有算法上的难度,要的就是你的细心和耐心,本人这道题的代码没有保存。

简单来说,为了实现目标函数find_settlement_date(),我写了几个子函数,字符串转换为vector<int>的函数(我用size为3的vector<int>来存储日期并进行运算),vector<int>转换为字符串的函数,对vector<int>代表的日期加一天得到新的日期的函数,

然后再在find_settlement_date()中调用这几个函数,注意leap year和周末的判断,字符串比较可以用string.compare()函数,参数是string,int转换为字符串调用to_string()函数,注意要加“0”。

第二题:

#include <bits/stdc++.h>

using namespace std;

string ltrim(const string &);
string rtrim(const string &);
vector<string> split(const string &);

/*
 * Do not attempt to modify the "Order" struct.
 */
struct Order {
    unsigned long id = 0;
    char side = ' ';
    unsigned short price = 0;
};


/*
 * Complete the "MatchingEngine" class below.
 */
class MatchingEngine
{
public:
    MatchingEngine()
    {
        
    }

    /* Return the id of the matching order, if any, otherwise return 0. */
    unsigned long insert(Order& order)
    {
        
    }
};
int main()
{
    ofstream fout(getenv("OUTPUT_PATH"));

    string order_count_temp;
    getline(cin, order_count_temp);
    int order_count = stoi(ltrim(rtrim(order_count_temp)));

    MatchingEngine engine;
    vector<long> result;
    result.reserve(order_count);

    for (int i = 0; i < order_count; i++)
    {
        string row_temp;
        getline(cin, row_temp);
        vector<string> row = split(rtrim(row_temp));

        Order o;
        o.id = stoi(ltrim(row[0]));
        o.side = row[1][0];
        o.price = stoi(ltrim(row[2]));

        long id = engine.insert(o);
        if (id != 0)
            result.push_back(id);
    }

    for (unsigned int i = 0; i < result.size(); i++)
    {
        fout << result[i] << "\n";
    }
    fout.close();

    return 0;
}

string ltrim(const string &str)
{
    string s(str);

    s.erase(
        s.begin(),
        find_if(s.begin(), s.end(), not1(ptr_fun<int, int>(isspace)))
    );

    return s;
}

string rtrim(const string &str)
{
    string s(str);

    s.erase(
        find_if(s.rbegin(), s.rend(), not1(ptr_fun<int, int>(isspace))).base(),
        s.end()
    );

    return s;
}

vector<string> split(const string &str)
{
    vector<string> tokens;

    string::size_type start = 0;
    string::size_type end = 0;

    while ((end = str.find(" ", start)) != string::npos)
    {
        tokens.push_back(str.substr(start, end - start));

        start = end + 1;
    }

    tokens.push_back(str.substr(start));
    return tokens;
}

 实现两个优先队列,并进行维护

代码如下:

class MatchingEngine
{
public:
	vector<Order> buy, sell;

	MatchingEngine()
	{

	}

	void build_buy(Order& order)
	{
		int i, n;

		buy.push_back(order);
		n = buy.size();
		if (n == 1) return;

		for (i = n-2; i >=0; i--)
		{
			if (order.price > buy[i].price)
				buy[i + 1] = buy[i];
			else
			{
				buy[i + 1] = order;
				return;
			}
		}
		buy[0] = order;
	}

	void build_sell(Order& order)
	{
		int i, n;

		sell.push_back(order);
		n = sell.size();
		if (n == 1) return;

		for (i = n - 2; i >= 0; i--)
		{
			if (order.price < sell[i].price)
				sell[i + 1] = sell[i];
			else
			{
				sell[i + 1] = order;
				return;
			}
		}
		sell[0] = order;
	}

	/* Return the id of the matching order, if any, otherwise return 0. */
	unsigned long insert(Order& order)
	{
		if (order.side == 'B')
		{
			if (sell.empty() || order.price < sell[0].price)
			{
				build_buy(order);
				return 0;
			}
			else
			{
				unsigned long tmp = sell[0].id;
				sell.erase(sell.begin());
				return tmp;
			}
		}
		else
		{
			if (buy.empty() || order.price > buy[0].price)
			{
				build_sell(order);
				return 0;
			}
			else
			{
				unsigned long tmp = buy[0].id;
				buy.erase(buy.begin());
				return tmp;
			}
		}
	}
};

总结:

optiver的面试题,不算难,也没有很高的算法要求,关键还是要细心

特色就是题目全英文,又臭又长,理解都要很长时间,外企可能都是这样吧。。。

猜你喜欢

转载自blog.csdn.net/LXQ1071717521/article/details/89076647