20

Is there a multiline string literal syntax in Matlab or is it necessary to concatenate multiple lines?

I found the verbatim package, but it only works in an m-file or function and not interactively within editor cells.

EDIT: I am particularly after readbility and ease of modifying the literal in the code (imagine it contains indented blocks of different levels) - it is easy to make multiline strings, but I am looking for the most convenient sytax for doing that.

So far I have

t = {...
'abc'...
'def'};
t = cellfun(@(x) [x sprintf('\n')],t,'Unif',false);
t = horzcat(t{:});

which gives size(t) = 1 8, but is obviously a bit of a mess.

EDIT 2: Basically verbatim does what I want except it doesn't work in Editor cells, but maybe my best bet is to update it so it does. I think it should be possible to get current open file and cursor position from the java interface to the Editor. The problem would be if there were multiple verbatim calls in the same cell how would you distinguish between them.

robince
  • 10,826
  • 3
  • 35
  • 48
  • I'm not sure I follow your question. can you add some examples that would clarify your goal? – Shai Jan 09 '13 at 11:33
  • 3
    Shai: I want to input a multiline string literal like `"""` in Python: eg to copy and paste a block of text (maintaining indentation) from another source into a matlab string. – robince Jan 09 '13 at 11:35

3 Answers3

13

I'd go for:

multiline = sprintf([ ... 
'Line 1\n'... 
'Line 2\n'... 
]);
Eric
  • 95,302
  • 53
  • 242
  • 374
edgar.holleis
  • 4,803
  • 2
  • 23
  • 27
  • 1
    I guess it trades the cell array messing for adding the newlines manually but pretty much the same idea... both make copying and pasting a literal block a bit of a pain! – robince Jan 09 '13 at 11:36
  • Get an editor that can do search/replace with regex and then replace \n by \\n\'...\n\' – edgar.holleis Jan 09 '13 at 11:37
  • 1
    You could use http://undocumentedmatlab.com/blog/editormacro-assign-a-keyboard-macro-in-the-matlab-editor/ to special-paste your text into the editor programmatically, doing the necessary substitution.s – edgar.holleis Jan 09 '13 at 11:49
  • 1
    Use `sprintf` to get the formatted multiline string. `fprintf` should be used for printing directly to screen. – sequielo Apr 09 '15 at 21:25
  • 1
    @sequielo: Edited to reflect that – Eric Feb 15 '17 at 23:40
6

Matlab is an oddball in that escape processing in strings is a function of the printf family of functions instead of the string literal syntax. And no multiline literals. Oh well.

I've ended up doing two things. First, make CR() and LF() functions that just return processed \r and \n respectively, so you can use them as pseudo-literals in your code. I prefer doing this way rather than sending entire strings through sprintf(), because there might be other backslashes in there you didn't want processed as escape sequences (e.g. if some of your strings came from function arguments or input read from elsewhere).

function out = CR()
out = char(13); % # sprintf('\r')

function out = LF()
out = char(10); % # sprintf('\n');

Second, make a join(glue, strs) function that works like Perl's join or the cellfun/horzcat code in your example, but without the final trailing separator.

function out = join(glue, strs)
strs = strs(:)';
strs(2,:) = {glue};
strs = strs(:)';
strs(end) = [];
out = cat(2, strs{:});

And then use it with cell literals like you do.

str = join(LF, {
    'abc'
    'defghi'
    'jklm'
    });

You don't need the "..." ellipses in cell literals like this; omitting them does a vertical vector construction, and it's fine if the rows have different lengths of char strings because they're each getting stuck inside a cell. That alone should save you some typing.

Andrew Janke
  • 23,508
  • 5
  • 56
  • 85
  • 2
    I am using Matlab r2007b, and the line cat(1, strs{:}); is not processed as expected, I get "CAT arguments dimensions are not consistent.". Could this be due to my old Matlab version? – RobertG Jan 12 '14 at 22:22
  • Well, for me, using the function call char(1, strs{:}); instead seems to work. – RobertG Jan 12 '14 at 22:29
  • @RobertG: You're right – it should be `cat(2, strs{:})` or `horzcat(strs{:})`. Silly oversight; sorry. Fixed. Calling `char(1, strs{:})` will probably produce a padded 2-D char array instead of one long char vector with embedded newlines, which may also be useful, but isn't what I was going for with `join()`. (The `cat(1,...)` will appear to work if all your input strings are the same length like OP's, but the output will be in the wrong format.) – Andrew Janke Mar 12 '14 at 22:27
3

Bit of an old thread but I got this

multiline = join([
"Line 1"
"Line 2"
], newline)

I think if makes things pretty easy but obviously it depends on what one is looking for :)