일반 텍스트 블록을 만드는 자동화된 좋은 방법이 있습니까?

일반 텍스트 블록을 만드는 자동화된 좋은 방법이 있습니까?

나는 종종 Mathematica에서 너무 길어서 읽을 수 없는 긴 방정식을 가져와서 C에 넣습니다. Mathematica는 80개의 문자 라인 블록에 잘 맞도록 제거하고 싶은 많은 개행 문자를 삽입합니다.

예를 들어:

(sin(T)*(16*pow(a,2)*M*cos(T)*pow(r,5)*
        pow(Th_d,2) - 
       8*pow(a,2)*cos(T)*pow(r,6)*pow(Th_d,2) + 
       M*pow(r,3)*(-((3*pow(a,2)*pow(Ee,2) - 8*pow(Jz,2) - 
                4*pow(a,2)*pow(Ee,2)*cos(2*T) + 
                pow(a,2)*pow(Ee,2)*cos(4*T))*Cot(T)*pow(csc(T),3))/
           2. + 32*pow(a,4)*pow(cos(T),3)*pow(Th_d,2)) - 
       2*(pow(a,4)*pow(Jz,2)*cos(T)*pow(Cot(T),4) + 
          4*pow(a,6)*pow(cos(T),5)*pow(r_d,2) + 
          4*pow(a,8)*pow(cos(T),5)*pow(Th_d,2)) - 
       2*pow(r,4)*(pow(Jz,2)*Cot(T)*pow(csc(T),3) + 
          4*pow(a,2)*cos(T)*pow(r_d,2) + 
          2*pow(a,4)*(5*cos(T) + cos(3*T))*pow(Th_d,2))\
        + (pow(a,2)*M*Cot(T)*pow(csc(T),3)*r*
          (4*(pow(a,2)*pow(Ee,2) - 2*a*Ee*Jz + 2*pow(Jz,2))*cos(2*T) - 
            a*Ee*(a*Ee - 2*Jz)*(3 + cos(4*T)) + 
            2*pow(a,4)*pow(sin(2*T),4)*pow(Th_d,2)))/2. + 
       pow(r,2)*(-16*pow(a,4)*pow(cos(T),3)*
           pow(r_d,2) - 
          4*pow(a,2)*pow(Cot(T),3)*csc(T)*
           (pow(Jz,2) + pow(a,4)*(5 + cos(2*T))*pow(sin(T),4)*
              pow(Th_d,2)))))/
   (4.*pow(pow(a,2)*pow(cos(T),2) + pow(r,2),2)*
     (pow(a,2) - 2*M*r + pow(r,2)))

될 것입니다

(sin(T)*(16*pow(a,2)*M*cos(T)*pow(r,5)*pow(Th_d,2) - 8*pow(a,2)*cos(T)*
pow(r,6)*pow(Th_d,2) + M*pow(r,3)*(-((3*pow(a,2)*pow(Ee,2) - 8*pow(Jz,2) - 
4*pow(a,2)*pow(Ee,2)*cos(2*T) + pow(a,2)*pow(Ee,2)*cos(4*T))*Cot(T)*pow(csc(T),3))/
2. + 32*pow(a,4)*pow(cos(T),3)*pow(Th_d,2)) - 2*(pow(a,4)*pow(Jz,2)*cos(T)*
pow(Cot(T),4) + 4*pow(a,6)*pow(cos(T),5)*pow(r_d,2) + 4*pow(a,8)*pow(cos(T),5)*
pow(Th_d,2)) - 2*pow(r,4)*(pow(Jz,2)*Cot(T)*pow(csc(T),3) + 4*pow(a,2)*cos(T)*
pow(r_d,2) + 2*pow(a,4)*(5*cos(T) + cos(3*T))*pow(Th_d,2)) + (pow(a,2)*M*Cot(T)*
pow(csc(T),3)*r*(4*(pow(a,2)*pow(Ee,2) - 2*a*Ee*Jz + 2*pow(Jz,2))*cos(2*T) - 
a*Ee*(a*Ee - 2*Jz)*(3 + cos(4*T)) + 2*pow(a,4)*pow(sin(2*T),4)*pow(Th_d,2)))/2. + 
pow(r,2)*(-16*pow(a,4)*pow(cos(T),3)*pow(r_d,2) - 4*pow(a,2)*pow(Cot(T),3)*csc(T)*
(pow(Jz,2) + pow(a,4)*(5 + cos(2*T))*pow(sin(T),4)*pow(Th_d,2)))))/(4.*pow(pow(a,2)*
pow(cos(T),2) + pow(r,2),2)*(pow(a,2) - 2*M*r + pow(r,2)));

가장 중요한 것은 아니지만 코드 길이를 줄이고 대용량 파일 작업에 더 적합합니다.

답변1

그것으로 sed당신은 할 수 있습니다

sed -E 'N;s/(.*)(\n) */\2\1/;/.{81}/s_^(.)(.{,79}[-+/*]) *_\2\1_;/^\n/!P;D' filename
  • -E확장 정규식을 사용하여 읽기 쉽게 만들기
  • N버퍼에 다음 줄 추가
  • s/(.*)(\n) */\2\1/줄을 연결하고 줄 바꿈을 처음으로 이동하고 들여쓰기된 공백을 제거합니다.
  • /.{81}/80자를 초과하는 줄에 유효합니다. 이 경우 s_^(.)(.{,79}[-+/*]) *_\2\1_개행 문자를 마지막 기호로 이동 하세요.
  • /^\n/!P버퍼의 첫 번째 줄이 비어 있지 않으면 인쇄합니다.
  • D나머지 버퍼부터 시작하세요

mosvy가 지적했듯이 이 스크립트에는 줄의 후행 백슬래시에 문제가 있으므로 이를 사용해야 합니다 . s/\\$//또한 더 긴 입력 줄이 있는 경우(OP의 문제는 아니지만 향후 독자를 위한 문제일 수 있음) . 전체 스크립트는 다음과 같습니다.N/.{80}/!N

sed -E 's/\\$//;/.{80}/!N;s/(.*)(\n) */\2\1/;/.{81}/s_^(.)(.{,79}[-+/*]) *_\2\1_;/^\n/!P;D' filename

관련 정보