Using `gsub` inside (double quoted) heredoc does not work












2















It appears that using gsub inside a (double quoted) heredoc does not evaluate the result of gsub, as follows:



class Test
def self.define_phone
class_eval <<-EOS
def _phone=(val)
puts val
puts val.gsub(/D/,'')
end
EOS
end
end

Test.define_phone
test = Test.new
test._phone = '123-456-7890'
# >> 123-456-7890
# >> 123-456-7890


The second puts should have printed 1234567890, just as it would in this case:



'123-456-7890'.gsub(/D/,'')
# => "1234567890"


What is going on inside the heredoc?










share|improve this question

























  • Note that you can accomplish this without class eval (and thus no worrying about string escaping). Just replace the class_eval and def _phone with define_method :_phone do |val|

    – Max
    Nov 26 '18 at 14:46
















2















It appears that using gsub inside a (double quoted) heredoc does not evaluate the result of gsub, as follows:



class Test
def self.define_phone
class_eval <<-EOS
def _phone=(val)
puts val
puts val.gsub(/D/,'')
end
EOS
end
end

Test.define_phone
test = Test.new
test._phone = '123-456-7890'
# >> 123-456-7890
# >> 123-456-7890


The second puts should have printed 1234567890, just as it would in this case:



'123-456-7890'.gsub(/D/,'')
# => "1234567890"


What is going on inside the heredoc?










share|improve this question

























  • Note that you can accomplish this without class eval (and thus no worrying about string escaping). Just replace the class_eval and def _phone with define_method :_phone do |val|

    – Max
    Nov 26 '18 at 14:46














2












2








2








It appears that using gsub inside a (double quoted) heredoc does not evaluate the result of gsub, as follows:



class Test
def self.define_phone
class_eval <<-EOS
def _phone=(val)
puts val
puts val.gsub(/D/,'')
end
EOS
end
end

Test.define_phone
test = Test.new
test._phone = '123-456-7890'
# >> 123-456-7890
# >> 123-456-7890


The second puts should have printed 1234567890, just as it would in this case:



'123-456-7890'.gsub(/D/,'')
# => "1234567890"


What is going on inside the heredoc?










share|improve this question
















It appears that using gsub inside a (double quoted) heredoc does not evaluate the result of gsub, as follows:



class Test
def self.define_phone
class_eval <<-EOS
def _phone=(val)
puts val
puts val.gsub(/D/,'')
end
EOS
end
end

Test.define_phone
test = Test.new
test._phone = '123-456-7890'
# >> 123-456-7890
# >> 123-456-7890


The second puts should have printed 1234567890, just as it would in this case:



'123-456-7890'.gsub(/D/,'')
# => "1234567890"


What is going on inside the heredoc?







ruby literals heredoc






share|improve this question















share|improve this question













share|improve this question




share|improve this question








edited Nov 26 '18 at 5:05









sawa

133k29206308




133k29206308










asked Nov 26 '18 at 3:18









DonatoDonato

2,13931435




2,13931435













  • Note that you can accomplish this without class eval (and thus no worrying about string escaping). Just replace the class_eval and def _phone with define_method :_phone do |val|

    – Max
    Nov 26 '18 at 14:46



















  • Note that you can accomplish this without class eval (and thus no worrying about string escaping). Just replace the class_eval and def _phone with define_method :_phone do |val|

    – Max
    Nov 26 '18 at 14:46

















Note that you can accomplish this without class eval (and thus no worrying about string escaping). Just replace the class_eval and def _phone with define_method :_phone do |val|

– Max
Nov 26 '18 at 14:46





Note that you can accomplish this without class eval (and thus no worrying about string escaping). Just replace the class_eval and def _phone with define_method :_phone do |val|

– Max
Nov 26 '18 at 14:46












1 Answer
1






active

oldest

votes


















5














The problem is with the D in the regex. It will be evaluated when the heredoc is evaluated as a string, which results in D:



"D" # => "D"
eval("/D/") #=> /D/


On the other hand, D inside a single quote will not be evaluated as D:



'D' # => "\D"
eval('/D/') # => /D/


So wrap the heredoc terminator EOS in a single quote to achieve what you want:



class Test
def self.define_phone
class_eval <<-'EOS'
def _phone=(val)
puts val
puts val.gsub(/D/,'')
end
EOS
end
end

Test.define_phone
test = Test.new
test._phone = '123-456-7890'
# >> 123-456-7890
# >> 1234567890


Reference



If you run the above code without the wrapped EOS, gsub will try to replace "D" (literally) in the val. See this:



test._phone = '123-D456-D7890DD'
# >> 123-D456-D7890DD
# >> 123-456-7890





share|improve this answer





















  • 3





    Or, another way is to replace D with \D.

    – sawa
    Nov 26 '18 at 4:54











  • Official reference: Literals - Here Documents

    – Stefan
    Nov 26 '18 at 9:12











Your Answer






StackExchange.ifUsing("editor", function () {
StackExchange.using("externalEditor", function () {
StackExchange.using("snippets", function () {
StackExchange.snippets.init();
});
});
}, "code-snippets");

StackExchange.ready(function() {
var channelOptions = {
tags: "".split(" "),
id: "1"
};
initTagRenderer("".split(" "), "".split(" "), channelOptions);

StackExchange.using("externalEditor", function() {
// Have to fire editor after snippets, if snippets enabled
if (StackExchange.settings.snippets.snippetsEnabled) {
StackExchange.using("snippets", function() {
createEditor();
});
}
else {
createEditor();
}
});

function createEditor() {
StackExchange.prepareEditor({
heartbeatType: 'answer',
autoActivateHeartbeat: false,
convertImagesToLinks: true,
noModals: true,
showLowRepImageUploadWarning: true,
reputationToPostImages: 10,
bindNavPrevention: true,
postfix: "",
imageUploader: {
brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
allowUrls: true
},
onDemand: true,
discardSelector: ".discard-answer"
,immediatelyShowMarkdownHelp:true
});


}
});














draft saved

draft discarded


















StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53474368%2fusing-gsub-inside-double-quoted-heredoc-does-not-work%23new-answer', 'question_page');
}
);

Post as a guest















Required, but never shown

























1 Answer
1






active

oldest

votes








1 Answer
1






active

oldest

votes









active

oldest

votes






active

oldest

votes









5














The problem is with the D in the regex. It will be evaluated when the heredoc is evaluated as a string, which results in D:



"D" # => "D"
eval("/D/") #=> /D/


On the other hand, D inside a single quote will not be evaluated as D:



'D' # => "\D"
eval('/D/') # => /D/


So wrap the heredoc terminator EOS in a single quote to achieve what you want:



class Test
def self.define_phone
class_eval <<-'EOS'
def _phone=(val)
puts val
puts val.gsub(/D/,'')
end
EOS
end
end

Test.define_phone
test = Test.new
test._phone = '123-456-7890'
# >> 123-456-7890
# >> 1234567890


Reference



If you run the above code without the wrapped EOS, gsub will try to replace "D" (literally) in the val. See this:



test._phone = '123-D456-D7890DD'
# >> 123-D456-D7890DD
# >> 123-456-7890





share|improve this answer





















  • 3





    Or, another way is to replace D with \D.

    – sawa
    Nov 26 '18 at 4:54











  • Official reference: Literals - Here Documents

    – Stefan
    Nov 26 '18 at 9:12
















5














The problem is with the D in the regex. It will be evaluated when the heredoc is evaluated as a string, which results in D:



"D" # => "D"
eval("/D/") #=> /D/


On the other hand, D inside a single quote will not be evaluated as D:



'D' # => "\D"
eval('/D/') # => /D/


So wrap the heredoc terminator EOS in a single quote to achieve what you want:



class Test
def self.define_phone
class_eval <<-'EOS'
def _phone=(val)
puts val
puts val.gsub(/D/,'')
end
EOS
end
end

Test.define_phone
test = Test.new
test._phone = '123-456-7890'
# >> 123-456-7890
# >> 1234567890


Reference



If you run the above code without the wrapped EOS, gsub will try to replace "D" (literally) in the val. See this:



test._phone = '123-D456-D7890DD'
# >> 123-D456-D7890DD
# >> 123-456-7890





share|improve this answer





















  • 3





    Or, another way is to replace D with \D.

    – sawa
    Nov 26 '18 at 4:54











  • Official reference: Literals - Here Documents

    – Stefan
    Nov 26 '18 at 9:12














5












5








5







The problem is with the D in the regex. It will be evaluated when the heredoc is evaluated as a string, which results in D:



"D" # => "D"
eval("/D/") #=> /D/


On the other hand, D inside a single quote will not be evaluated as D:



'D' # => "\D"
eval('/D/') # => /D/


So wrap the heredoc terminator EOS in a single quote to achieve what you want:



class Test
def self.define_phone
class_eval <<-'EOS'
def _phone=(val)
puts val
puts val.gsub(/D/,'')
end
EOS
end
end

Test.define_phone
test = Test.new
test._phone = '123-456-7890'
# >> 123-456-7890
# >> 1234567890


Reference



If you run the above code without the wrapped EOS, gsub will try to replace "D" (literally) in the val. See this:



test._phone = '123-D456-D7890DD'
# >> 123-D456-D7890DD
# >> 123-456-7890





share|improve this answer















The problem is with the D in the regex. It will be evaluated when the heredoc is evaluated as a string, which results in D:



"D" # => "D"
eval("/D/") #=> /D/


On the other hand, D inside a single quote will not be evaluated as D:



'D' # => "\D"
eval('/D/') # => /D/


So wrap the heredoc terminator EOS in a single quote to achieve what you want:



class Test
def self.define_phone
class_eval <<-'EOS'
def _phone=(val)
puts val
puts val.gsub(/D/,'')
end
EOS
end
end

Test.define_phone
test = Test.new
test._phone = '123-456-7890'
# >> 123-456-7890
# >> 1234567890


Reference



If you run the above code without the wrapped EOS, gsub will try to replace "D" (literally) in the val. See this:



test._phone = '123-D456-D7890DD'
# >> 123-D456-D7890DD
# >> 123-456-7890






share|improve this answer














share|improve this answer



share|improve this answer








edited Nov 26 '18 at 5:03









sawa

133k29206308




133k29206308










answered Nov 26 '18 at 4:51









Lenin Raj RajasekaranLenin Raj Rajasekaran

16.1k1173115




16.1k1173115








  • 3





    Or, another way is to replace D with \D.

    – sawa
    Nov 26 '18 at 4:54











  • Official reference: Literals - Here Documents

    – Stefan
    Nov 26 '18 at 9:12














  • 3





    Or, another way is to replace D with \D.

    – sawa
    Nov 26 '18 at 4:54











  • Official reference: Literals - Here Documents

    – Stefan
    Nov 26 '18 at 9:12








3




3





Or, another way is to replace D with \D.

– sawa
Nov 26 '18 at 4:54





Or, another way is to replace D with \D.

– sawa
Nov 26 '18 at 4:54













Official reference: Literals - Here Documents

– Stefan
Nov 26 '18 at 9:12





Official reference: Literals - Here Documents

– Stefan
Nov 26 '18 at 9:12




















draft saved

draft discarded




















































Thanks for contributing an answer to Stack Overflow!


  • Please be sure to answer the question. Provide details and share your research!

But avoid



  • Asking for help, clarification, or responding to other answers.

  • Making statements based on opinion; back them up with references or personal experience.


To learn more, see our tips on writing great answers.




draft saved


draft discarded














StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53474368%2fusing-gsub-inside-double-quoted-heredoc-does-not-work%23new-answer', 'question_page');
}
);

Post as a guest















Required, but never shown





















































Required, but never shown














Required, but never shown












Required, but never shown







Required, but never shown

































Required, but never shown














Required, but never shown












Required, but never shown







Required, but never shown







Popular posts from this blog

Wiesbaden

Marschland

Dieringhausen