[42seoul] Get_Next_Line

ppparkta·2022년 7월 29일
0

42Seoul

목록 보기
4/10

get next line

사전지식

  • open(), read() return value
  • file descriptor
  • static

open()

int open(const char *path, int oflag, ...)

첫번째 인자: 읽을 파일의 경로
두번째 인자: 파일 read할 때 사용하는 옵션

  • 반환값1: 읽은 파일의 fd번호
  • 반환값2: 음수는 open 실패한 경우

read()

ssize_t read(int fildes, void *buf, size_t nbyte)

nbyte만큼 fildes로부터 데이터를 읽어들여서 buf에 저장하려고 시도한다.

  • 반환값1: 성공적으로 읽었다면 read한 byte만큼 리턴한다.
  • 반환값2: 파일이 끝나면 0을 리턴한다.
  • 반환값3: 읽기에 실패하면 -1리턴하고 errno 설정한다.

ssize_t 는 부호 있는 8바이트 정수

open한 파일을 fd로부터 읽어들여야 함. 이때 사용하는게 read함수임.

close()

int close(int fildes)

해당 프로세스의 파일테이블에서 fd를 삭제한다.

  • 반환값1: 성공할 경우 0 리턴
  • 반환값2: 실패할 경우 -1 리턴하고 errno 설정

구현

mand

get_next_line

char	*get_next_line(int fd)
{
	char				*line;
	static char			*left_str;
	//디스크립터 번호가 잘못됐거나 버퍼 설정이 잘못됐을 때 널 반환
	if (fd < 0 || BUFFER_SIZE <= 0)
		return (0);
	//ft_buff() 개행이나 eof를 포함해 read로 문자열을 읽는 함수
	left_str = ft_buff(fd, left_str);
	//left_str이 널이라면 ft_buff에서 read가 실패했다는 뜻이므로 널 반환
	if (!left_str)
		return (NULL);
	//ft_get_line() 개행이나 eof기준으로 문자 복사하는 함수
	line = ft_get_line(left_str);
	//ft_last_str() line으로 온 값 제외하고 남은 문자열 백업에 넣는 함수
	left_str = ft_last_str(left_str);
	return (line);
}

ft_get_line

char	*ft_get_line(char *left_str)
{
	char	*str;
	int		i;

	i = 0;
	//만약 백업 스트링의 시작글자가 널이라면 자를게 없음
	if (!left_str[i])
		return (NULL);
	//글자수 세기
	while (left_str[i] && left_str[i] != '\n')
		i++;
	//개행문자 + 널문자 자리 확보해야되므로 2 더해서 엠얼록
	str = (char *)malloc(sizeof(char) * (i + 2));
	//널가드
	if (!str)
		return (NULL);
	i = 0;
	//eof일수도 있고 개행일수도 있는데 if문으로 분기함
	while (left_str[i] && left_str[i] != '\n')
	{
		str[i] = left_str[i];
		i++;
	}
	if (left_str[i] == '\n')
	{
		str[i] = left_str[i];
		i++;
	}
	str[i] = '\0';
	return (str);
}

ft_last_str

char	*ft_last_str(char *left_str)
{
	int		i;
	int		j;
	char	*str;

	i = 0;
	while (left_str[i] && left_str[i] != '\n')
		i++;
	//이렇게 넘어갔는데 0이면 반환이 잘못됨 or EOF 이므로 백업을 free
	if (!left_str[i])
	{
		free(left_str);
		return (NULL);
	}
	//left_str의 전체 문자열에서 line으로 반환한 부분만큼 빼내고 널문자 포함하여 엠얼록
	str = (char *)malloc(sizeof(char) * (ft_strlen(left_str) - i + 1));
	//널가드
	if (!str)
		return (NULL);
	i++;
	j = 0;
	while (left_str[i])
		str[j++] = left_str[i++];
	str[j] = '\0';
	free(left_str);
	return (str);
}

ft_buff

char	*ft_buff(int fd, char *left_str)
{
	int		rd_bytes;
	char	*buff;

	buff = malloc(sizeof(char) * (BUFFER_SIZE + 1));
	//널가드
	if (!buff)
		return (NULL);
	//rd_bytes=read로 받아온 값, 처음에는 문제가 없다는 뜻으로 1로 초기화함
	rd_bytes = BUFFER_SIZE;
	//개행문자가 나오지 않고 파일의 끝이 아닌동안 반복
	while (!ft_strchr(left_str, '\n') && rd_bytes == BUFFER_SIZE)
	{
		rd_bytes = read(fd, buff, BUFFER_SIZE);
		//read가 잘못됐을 때 free
		if (rd_bytes == -1)
		{
			free(left_str);
			free(buff);
			return (NULL);
		}
		//버퍼 크기만큼 읽어왔다면 마지막에 널문자를 붙여서 조인에 씀
		buff[rd_bytes] = '\0';
		left_str = ft_strjoin(left_str, buff);
	}
	free(buff);
	return (left_str);
}
profile
겉촉속촉

0개의 댓글

관련 채용 정보