improve the function