/ * লাইন নম্বর মন্তব্যগুলি তৈরি করুন * /


12

আপনার কাজটি এমন একটি প্রোগ্রাম (বা ফাংশন) লিখতে হবে যা ইনপুট হিসাবে একটি স্ট্রিং নেবে এবং প্রতিটি লাইনের শুরুতে পাঠ্য সংযোজন করবে যা নিম্নলিখিত বিধিগুলি পূরণ করে:

  • সংযুক্ত পাঠ্যটিতে অবশ্যই লাইন নম্বর থাকা উচিত। আপনি 0- বা 1-ভিত্তিক সূচক ব্যবহার করতে পারেন।
  • পাঠ্যটি অবশ্যই আপনার ভাষায় একটি মন্তব্য হওয়া উচিত। একটি মন্তব্য সিন্ট্যাকটিক্যালি বৈধ কোড হিসাবে সংজ্ঞায়িত করা হয়েছে যা প্রোগ্রামের রাজ্যে কোনও পরিবর্তন করে না। মন্তব্য সরানো প্রোগ্রামে কোন পরিবর্তন করা উচিত।
  • মন্তব্যে এটির শেষে কেবল নতুন লাইন থাকতে পারে।
  • আপনার কেবল লাইফ স্পেস এবং মন্তব্য থাকা লাইনের জন্য লাইন নম্বর রাখতে হবে না।

বিশেষ উল্লেখ

  • আপনি ধরে নিতে পারেন যে ইনপুটটি আপনার ভাষায় একটি বৈধ প্রোগ্রাম হবে।
  • পাইথনের মতো ইন্ডেন্টেশন-সংবেদনশীল ভাষায়, আপনি সমস্ত ইনডেন্টেশনের পরে লাইন নম্বর মন্তব্য রাখতে পারেন। আপনি আপনার ইনডেন্টেশন চরিত্র হতে ট্যাব বা স্পেস দুটি বেছে নিতে পারেন, তবে আপনাকে অবশ্যই আপনার পোস্টে নির্দিষ্ট করতে হবে।
  • আপনি ধরে নিতে পারেন যে কোডটির প্রতিটি বিবৃতি সর্বাধিক 1 লাইনের সম্পূর্ণতা গ্রহণ করবে; অর্থাত্ কোনও মাল্টি-লাইন স্ট্রিং বা ব্যাকস্ল্যাশ-ধারাবাহিকতা নেই।

পরীক্ষার কেস

পাইথন:

#0
a = int(input())
#1
while a:
    #2
    print(a)

সি: (সত্যই, আমি এই সংকলনগুলি অবাক করে দিয়েছি)

/*0 */#include <stdio.h>
/*1 */int main()
/*2 */{
/*3 */    char c;
/*4 */    c = getchar();
/*5 */    do
/*6 */    {
/*7 */        putchar(c);
/*8 */    }
/*9 */    while (c);
/*10*/}

এটি , তাই সংক্ষিপ্ত উত্তরটি (বাইটে) জেতে।


7
ভাষা-নির্ভর মন্তব্য করা বিষয়গুলিকে জটিল করে তোলে। পাইথনের জন্য আপনাকে ইতিমধ্যে একটি বিশেষ নিয়ম তৈরি করতে হয়েছিল। অন্যান্য সমস্ত ভাষাগুলির কী বিষয়ে যেগুলিতে মাল্টি-লাইন মন্তব্য নেই? এমন ভাষাগুলি সম্পর্কে যা সম্পর্কে কোনও মন্তব্য নেই। মাল্টি-লাইন স্ট্রিংগুলি সম্পর্কে কী যেখানে পার্শ্ব প্রতিক্রিয়া ছাড়াই মন্তব্যগুলি রাখা যায় না?
ডেনিস

4
মজাদার ঘটনা: নিয়ম "মন্তব্য সরানো উচিত প্রোগ্রামে কোনও পরিবর্তন করা উচিত নয়" তত্ক্ষণাত কোনও পাইথন উত্তর অযোগ্য করে দেয়, কারণ কোড সহ মন্তব্যগুলি run রানটাইমটিতে অন্তর্নিম্ন করা যেতে পারে। আমি এটি একটি প্রোডাকশন সিস্টেমে খেলতে দেখেছি: AssertionErrorস্ট্যাক ট্রেসটিতে বাক্যাংশটি না থাকলে একটি কোডের টুকরো একটি উত্থাপন করতে পারে foo.py, যা কোনও ফাইলের নাম থেকে প্রত্যাশিত ছিল তবে প্রসঙ্গে একটি লাইন মন্তব্য হিসাবে উপস্থিত হতে পারে।
wchargin

2
" মন্তব্যে এটির শেষে কেবলমাত্র নিউলাইনগুলি থাকতে পারে " সি " টেস্ট কেস " এর সাথে বেমানান ।
পিটার টেলর

2
মন্তব্য না করে ল্যাংগের কী হবে?
NoOneIs এখানে

4
সম্পাদনা অসঙ্গতি ঠিক করে না।
পিটার টেলর

উত্তর:


5

পাইকে, 7 বাইট

o\Kz++r

এখানে চেষ্টা করুন!

o       -  o++
 \K     -  "K"
   z    -  input()
    ++  - sum(^)
      r - while no errors: GOTO start

আমি পূর্ণসংখ্যার মন্তব্যগুলি অক্ষরের Kএবং তারপরে লাইন অনুসারে পূর্ণসংখ্যা হিসাবে ঘোষণা করছি । নিউলাইন অপকোডকে অতিরিক্ত জিনিস লাথি মেরে এবং মুদ্রণ করা থেকে বিরত রাখতে অতিরিক্ত বাইট ব্যবহার করা হয়।


16

পার্ল, 8 + 1 = 9 বাইট

say"#$."

-p(1 বাইট পেনাল্টি) দিয়ে চালান । (পিপিসিজি নিয়মের সাথে অপরিচিত লোকদের জন্য দ্রষ্টব্য; আপনার ব্যবহার করে পার্ল সিনট্যাক্সের একটি আধুনিক সংস্করণও উল্লেখ করতে হবে -M5.010, তবে আমরা সিদ্ধান্ত নিয়েছি যে ভাষা সংস্করণ নির্বাচন করার বিকল্পগুলি নিখরচায় এবং বাইট জরিমানা ব্যয় করতে হবে না, তাই আমি এটিতে উল্লেখ করি নি এই পোস্টের মূল সংস্করণ।)

-pপ্রোগ্রামকে একটি অন্তর্নিহিত লুপে রাখে; এটি মূলত প্রোগ্রামটিকে ফিল্টারে পরিণত করে যা প্রতিটি লাইনকে পৃথকভাবে প্রক্রিয়াজাত করে (যেমন পুরো প্রোগ্রামটি প্রথম লাইনে চালিত হয়, তারপরে দ্বিতীয়, তৃতীয় এবং আরও অনেক কিছু)। পার্ল একটি লাইন নাম্বারও ট্র্যাক করে রাখে, যাকে বলা হয় $.যে ইনপুটটির কতগুলি লাইন পড়েছে তা রেকর্ড করে। সুতরাং সমস্ত প্রোগ্রাম করছে -pইনপুট একটি লাইন পড়তে দেওয়া ; আউটপুট এ #, বর্তমান লাইন নম্বর ( $.) এবং একটি নতুন লাইন ( sayডিফল্টরূপে একটি নতুন লাইন যুক্ত করে, যা এই ক্ষেত্রে সহায়ক, এবং সাধারণভাবে দেখা যায় তার চেয়ে ছোটও হয় print); এবং তারপরে -pআউটপুটটিকে কোডের মূল লাইনটি দেওয়া (সাধারণত কোনও প্রোগ্রাম ব্যবহার করে)-pইনপুটটিতে কিছু প্রক্রিয়াকরণ করবে, কিন্তু আমরা না করায় এটি কেবল আউটপুট অপরিবর্তিত)। পার্লের মন্তব্যগুলি #একটি নতুন লাইনে চলেছে ( #প্রোগ্রামটিতে নিজেই কোনও মন্তব্য শুরু করে না কারণ এটি একটি স্ট্রিং আক্ষরিক অভ্যন্তরের অভ্যন্তরে), তাই আমরা মূলত যা করছি তা ফাইলটিতে মন্তব্য লাইনগুলি লেখার সুযোগ গ্রহণ করা হচ্ছে যখন আমরা এটি প্রক্রিয়া করি , "প্রাকৃতিক" পড়তে এবং লেখার চক্রটিকে বিরক্ত না করে -p


এটি কীভাবে কাজ করে তা ব্যাখ্যা করতে পারেন?
Adám

অবশ্যই। আমি টিউটোরিয়াল স্টাইলে প্রাসঙ্গিক পার্ল ভাষার বৈশিষ্ট্যগুলির ক্রিয়াকলাপটি ব্যাখ্যা করেছি, প্রদত্ত যে এটি একটি খুব প্রাথমিক পার্ল প্রোগ্রাম যা ভাষার শক্তির সত্যই বেশি ব্যবহার করে না। আমার মনে রাখতে হবে যে কীভাবে -pলুপ বা স্বয়ংক্রিয়ভাবে আপডেট হওয়া লাইন নম্বরটি কাজ করে তা সবাই জানে না ।

দ্রষ্টব্য say"$.;"এটিও কাজ করবে, কারণ প্রশ্নটি উল্লেখ করেছে যে "আপনি ধরে নিতে পারেন কোডের প্রতিটি বিবৃতি সর্বাধিক 1 লাইনের সম্পূর্ণতা গ্রহণ করবে"।
msh210

যদিও এটি আসলে কোনও মন্তব্য নয়; যদিও এটি কার্যকর কিছু করে না, এটি এএসটিতে শেষ হয় (এবং কারণ পার্লের অপটিমাইজারটি ধৈর্যপূর্ণ, তাই আমি মনে করি যে আসলে প্রোগ্রামটি ধীর করে দেবে, এমন কোনও কিছু যা আপনি আসলে মন্তব্য করতে চান না)।

নিয়মের জন্য কাজ করছে না আপনাকে লাইন নম্বরগুলি রেখার জন্য লাগাতে হবে না যেখানে কেবল শ্বেতস্থান এবং মন্তব্য রয়েছে।
ডেনিস ইবায়েভ

9

জাভাস্ক্রিপ্ট, 43 39 বাইট

a=>a.replace(/^/gm,_=>`/*${++b}*/`,b=0)

4 টি বাইট সংরক্ষণের জন্য ETH এবং কনরকে ধন্যবাদ।


41 বাইট: a => (বি = 0, এ রিপ্লেস (/ ^ / জিএম, _ => /*${++b}*/)) (একটি ফর্ম্যাটিং স্ট্রিং ব্যবহার করুন)
কনার ও ব্রায়ান

1
39 বাইট:a=>a.replace(/^/gm,_=>`/*${++b}*/`,b=0)
ETH প্রোডাকশন


3

ব্যাচ, 91 বাইট

@set n=
@for /f "delims= tokens=*" %%a in (%1) do @set/an+=1&call echo @rem %%n%%&echo %%a

ইওএফ না হওয়া পর্যন্ত ব্যাচের স্টাডিন পড়ার উপায় নেই, সুতরাং পরিবর্তে ফাইলের নাম কমান্ড-লাইন প্যারামিটার হিসাবে পাস করতে হবে।


3

লুয়া, 80 75 বাইট

ল্যাংকে গালি দিয়ে কিছু বাইট সংরক্ষণ করেছেন।

x=1print("--[[1]]"..(...):gsub("\n",load('x=x+1return"\\n--[["..x.."]]"')))

সহজ যথেষ্ট স্টার্টার উত্তর।

অবহেলিত, +

x=1                                                     -- Assign x to 1...
print(                                                  -- Print...
      "--[[1]]"                                         -- The first line number comment...
      ..                                                -- With...
      (...):gsub(                                       -- The input, replacing all...
                 "\n",                                  -- Newlines...
                    load                                -- with a string compiled function...
                    (' \
                    x=x+1                               --Increment x by one... \
                    return"\\n--[["..x.."]]"            -- And return the new linecomment. \
                    ')
                 )
      )

আমি লুয়া জানি না, তবে আপনি কি নিশ্চিত যে এটি সর্বদা একই দৈর্ঘ্যের মতামত উত্পন্ন করবে? উদাহরণস্বরূপ, যদি কোনও প্রোগ্রামটি শেষ মন্তব্যের চেয়ে 10 লাইন দীর্ঘ --[[10]]হয় --[[9]]তবে আপনি যদি স্পেস দিয়ে সঠিকভাবে প্যাড না করেন তবে 1 অক্ষর দীর্ঘ হবে।
Esolanging ফল

1
ওহ, আমি সেই নিয়মটি লক্ষ্য করিনি। মনে হচ্ছে ... কিছুটা রিডানড্যান্ট ...
এটিাকো

1
হ্যাঁ. সম্ভবত আমি এটিকে সরিয়ে দেব ... [সম্পাদনা]: সরানো হয়েছে।
Esolanging ফল

3

গেমা, 16 15 টি অক্ষর

*\n=\!@line\n$0

গেমায় কেবলমাত্র লাইন মন্তব্য রয়েছে, দিয়ে শুরু !

নমুনা রান:

bash-4.3$ cat l33t.gema 
e=3
g=9
i=1
o=0
t=7

bash-4.3$ gema -f l33t.gema <<< 'Hello World!'
H3ll0 W0rld!

bash-4.3$ gema '*\n=\!@line\n$0' < l33t.gema > l33t-nr.gema

bash-4.3$ cat l33t-nr.gema
!1
e=3
!2
g=9
!3
i=1
!4
o=0
!5
t=7

bash-4.3$ gema -f l33t-nr.gema <<< 'Hello World!'
H3ll0 W0rld!

অ্যাডামের প্রশ্নের উত্তর দেওয়ার জন্য নিম্নলিখিতগুলি উপেক্ষা করা কোডের মতো লাইন নম্বর যুক্ত করা সম্ভব কিনা whether

Gema কোড মূলত একটি সংগ্রহ থেকে = থেকে রূপান্তর বিধি, বা টেমপ্লেট = কর্ম Gema পদ। আমি কোনও টেমপ্লেট সংজ্ঞায়নের কোনও উপায় দেখতে পাচ্ছি না যা কখনই কোনও কিছুর সাথে মেলে না, এটি একা মনে হয় না।

গেমার, 18 টি অক্ষর

*\n=c:\=@line\;:$0

বদলে দেয় e=3মধ্যে c:=1;:e=3

ভাগ্যক্রমে গেমায় রয়েছে ডোমেন , ধরনের নামস্থান sp উপরের কোডটি নেমস্পেস সিতে ডামি বিধিগুলি সংজ্ঞায়িত করে, যা আমরা কখনই ব্যবহার করি না। দুর্ভাগ্যক্রমে একটি উল্লিখিত ডোমেনটি লাইনের শেষ অবধি কার্যকর থাকে, সুতরাং আমাদের স্পষ্টভাবে ডিফল্ট ডোমেনে ফিরে যেতে হবে।

গেমার, 18 টি অক্ষর

*\n=@line\=\$0\;$0

বদলে দেয় e=3মধ্যে 1=$0;e=3

একটি কম জটিল বিকল্প হ'ল উপেক্ষা করা পরিবর্তে ফলশূন্য কোড ব্যবহার করা। মানে যা ঠিক মিলেছিল তা ফিরিয়ে দিতে চাই।


তবে আপনি কি একটি স্ট্রিং sertোকাতে এবং এর চারপাশে কিছু কোড রাখতে পারবেন না যা এটিকে উপেক্ষা করে?
অ্যাডম

আপনি e=3বর্তমানের if (false) { 1 }; e=3পরিবর্তে এক ধরণের রূপান্তর বোঝাতে চান !1␤e=3? হ্যাঁ, একটি 19 চরিত্র দীর্ঘ workaround হবে।
manatwork

2

Qbasic, 91 89 বাইট

OPEN"I",1,"i"
OPEN"O",2,"o"
DO UNTIL EOF(1)
i=i+1
INPUT#1,a$
PRINT#2,STR$(i)+"'"+a$
LOOP

ইনপুট:

CLS
PRINT "Hello!"
a$="Welcome"
INPUT "Type your name: ", b$
PRINT a$; ", "; b$
END

আউটপুট:

 1'CLS
 2'PRINT "Hello!"
 3'a$="Welcome"
 4'INPUT "Type your name: ", b$
 5'PRINT a$; ", "; b$
 6'END

1
কিউ বেসিক ব্যবহার করার পরে কিছুক্ষণ হয়ে গেছে, তবে প্রোগ্রামের পাঠ্যটি লাইনের সংখ্যাগুলির চেয়ে সমস্ত মন্তব্য করে না? নাকি আমি কিছু ভুল করে দিচ্ছি?

ইনপুট জন্য ধন্যবাদ! প্রকৃতপক্ষে, 'কেবল মন্তব্যগুলি লাইনে অনুসরণ করে।
বেনামে 2

4
হ্যাঁ, তাই আমি মনে করি এটি প্রোগ্রামকে মন্তব্যগুলিতে পরিণত করছে। কেবল লাইন সংখ্যা যুক্ত করার পরিবর্তে, এর অর্থ এমন একটি প্রোগ্রামে পরিবর্তিত হয় যা কিছুই করে না। (সত্য, সত্যিকারের লাইন নম্বর যুক্ত করতে এবং প্রোগ্রামটির যদি ইতিমধ্যে সংখ্যা রয়েছে তবে প্রোগ্রামটি পুনর্নির্মাণের জন্য এটি বেসিক উপভাষায় প্রবেশের পক্ষে শান্ত হবে তবে সম্ভবত এটি সত্যই দরকার নেই))

2

বেস (+ জিএনইউ সেড) 27 বাইট

sed 'i#
='|sed 'N;s/\n//;N'

প্রথম অংশটি ( i# \n =জিএনইউ সেডে প্রায় 4 টি বাইটের জন্য) কাজ করে তবে এটি পরে একটি নতুন লাইন রাখে #


2

জেউ ( 19 13 বাইট)

19 বাইট : এই কোডের প্রতিটি লাইনের উপরে "#" + লাইন নম্বর সন্নিবেশ করান

{print"#"NR"\n"$0}

13 বাইট : ক্রেডিট এবং দুটি 13 বাইট সমাধানের জন্য @ মান্যাটওয়ার্ককে ধন্যবাদ

1কর্মটি ডিফল্ট হিসাবে print $0:

{print"#"NR}1

বা $0বিষয়বস্তু প্রতিস্থাপন করে

$0="#"NR RS$0

{print"#"NR}1বা $0="#"NR RS$0?
manatwork

@ মান্যাটওয়ার্ক আমি এই লৌকিকতাগুলি আবিষ্কার করতে আমি বেশ লজ্জিত এবং কৃতজ্ঞ
অ্যাডাম

2

কোটলিন এক্সটেনশন ফাংশন, 69 60 বাইট

fun String.a()=lines().mapIndexed{i,s->"/*$i*/$s"}.joinToString("\n")

fun String.a(){lines().mapIndexed{i,s->println("/*$i*/$s")}}

ব্যবহারের উদাহরণ:

fun main(args: Array<String>) {
  //language=kotlin
  val code = """fun main(args: Array<String>) {
  println("Hello world!")
}"""
  code.a()
}

আউটপুট:

/*0*/fun main(args: Array<String>) {
/*1*/  println("Hello world!")
/*2*/}

1

সিজেম, 21 বাইট

আমি সিজেমে মোটেও পারদর্শী নই, তবে আমি জানতাম যে এটির মন্তব্য রয়েছে :)

qN%ee{"e#"o(oNo(oNo}/

ব্যাখ্যা শীঘ্রই আসছে।


oNonটিআইও দিয়ে প্রতিস্থাপন করা যেতে পারে ।
এশালং ফলমূল

1

গণিত, 58 বাইট

i = 1; StringReplace[#, StartOfLine :> "(*" <> ToString@i++ <> "*)"] &

1

jq, 31 টি অক্ষর

(২ characters টি অক্ষরের কোড + ৪ টি অক্ষরের কমান্ড লাইন বিকল্প)

"#\(input_line_number)\n"+.

জিকিউতে কেবলমাত্র লাইন মন্তব্য রয়েছে, দিয়ে শুরু করা #

নমুনা রান:

bash-4.3$ cat l33t.jq 
gsub("e";"3")|
gsub("g";"9")|
gsub("i";"1")|
gsub("o";"0")|
gsub("t";"7")

bash-4.3$ jq -Rr -f l33t.jq <<< 'Hello World!'
H3ll0 W0rld!

bash-4.3$ jq -Rr '"#\(input_line_number)\n"+.' l33t.jq > l33t-nr.jq

bash-4.3$ cat l33t-nr.jq 
#1
gsub("e";"3")|
#2
gsub("g";"9")|
#3
gsub("i";"1")|
#4
gsub("o";"0")|
#5
gsub("t";"7")

bash-4.3$ jq -Rr -f l33t-nr.jq <<< 'Hello World!'
H3ll0 W0rld!

প্রিয় পার্ল ও রুবির পরিকল্পনাটি, এর jq মান্য করুন input_line_number। থ্যাঙ্কসগিভিং হচ্ছে, কোন বিশেষ অনুভূতি প্রকাশের জন্য $.?
manatwork

1

গল্ফস্ক্রিপ্ট, 23 বাইট

n/0:i;{"#"i):i+n+\+}%n*

"#" দিয়ে শুরু কেবল লাইন মন্তব্য রয়েছে।

অবহেলিত এবং ব্যাখ্যা:

           # the input is pushed on the stack automatically
n          # n is a predefined variable for "\n"
/          # splits the input string with the previously pushed "\n" as delimiter
0:i;       # i = 0
{          # A code block: It is used for map here (going through the input)
    "#"    # push a "#" onto the stack
    i):i  # save i + 1 in i, the value is again not popped from the stack
    +      # implicitly converts the number i to a string and concatenates "#" with it
    n      # newline
    +      # add a newline (# introduces a *line* comment)
    \      # switch the top to elements (-> yields the comment as the bottom, and the line as the top element on the stack)
    +      # concatenate them
}          # end of the code block
%          # map
n          # newline
*          # join the list with newlines between them
           # outputs are done implicitly

আমি নিশ্চিত যে এটিকে আরও সরলীকরণ করা যায়, বিশেষত iসম্ভবত এটি বাদ দেওয়া যেতে পারে।

আপনি এটি এখানে পরীক্ষা করতে পারেন: https://golfscript.apphb.com/ যেহেতু এই সাইটটি ইনপুট যুক্ত করা সমর্থন করে না, আপনাকে কোডের সামনে ডাবল উদ্ধৃতি দ্বারা বেষ্টিত একটি স্ট্রিং রাখতে হবে। '\n'একটি নতুন লাইন হবে। এই বিষয়টি সম্পর্কে সচেতন থাকুন, অন্যান্য পালানোর ক্রমও রয়েছে। ব্যবহারকারী '\\'আপনি নিশ্চিত না হলে।


1

সি # 6, 66 61 বাইট

সিএসারপিকে ধন্যবাদ

(6 666, শয়তান কোড ^^) আর নেই ...

এটি "সি স্টাইল মন্তব্য" (সি, সি ++, সি #, জাভা, ....) ব্যবহার করে সমস্ত ভাষার জন্য কাজ করে

এটি স্ট্রিংকে কেবল রেখায় বিভক্ত করে, প্রতিটি সূত্রকে তার সূচকের সাথে সংশোধন করে এবং আবার নতুন রেখার অক্ষরের সাথে সম্পাদিত রেখাগুলিতে যোগ দেয়।

s=>string.Join("\n",s.Split('\n').Select((l,i)=>$"/*{i}*/"+l));

পুরনো সংস্করণ:

s=>string.Join("\n",s.Split('\n').Select((l,i)=>$"/*{i,3}*/{l}"));

1
টেকনিক্যালি 64 যেহেতু অপেরা জিরোগুলির সাথে কোনও প্যাডিংয়ের কথা উল্লেখ করেনি। এছাড়াও আপনি আরও 1 টি বাইট ফাঁক করে বাঁচাতে পারবেন: $ "/ * {i} * /" + l। (
অন্তরঙ্গ

আপনি ঠিক বলেছেন - তবে এটি আমার "অশুভ স্কোর" কে ধ্বংস করে দেয়
স্টিফান

0

পাইথন 2, 82 বাইট

কেবল স্থান ফাঁকা করার জন্য কাজ করে

for i,l in enumerate(input().split('\n')):print l.split(l.lstrip())[0]+'#%d\n'%i+l

56 বাইটের জন্য ইনডেন্টেশন-কম সংস্করণ

for x in enumerate(input().split('\n')):print'#%d\n%s'%x
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.